[POI2015]PUS [线段树优化建图]

problem

线段树优化建图,拓扑,没了。

#include <bits/stdc++.h>

#define ls(x) ch[x][0]
#define rs(x) ch[x][1]
#define rep(i , j , k) for(int i = j ; i <= k ; i ++)
#define Rep(i , j , k) for(int i = j ; i >= k ; i --)

using namespace std ;
using ll = long long ;
using pii = pair <int , int> ;
using vii = vector <int> ;
// #define int long long
auto ot = [&]() { cerr << "ATS TXDY" << '\n' ; int ATS_nantf_txdy = true ; } ;
auto _ios = [&]() { ios :: sync_with_stdio(false) ; cin.tie(nullptr) ; cout.tie(nullptr) ; } ;

namespace stO_ATS_Orz {
  template < class T > void cmax(T & x , T y) { if(x < y) x = y ; }
  template < class T > void cmin(T & x , T y) { if(x > y) x = y ; }
  template < class T > void abs(T x) { if(x < 0) x = -x ; }
  int n , s , m ;
  const int N = 1e5 + 10 ;
  const int M = 2e5 + 10 ;
  const int limit = 1e9 ;
  struct Edge { int v , nxt , w ; } e[N * 30] ;
  int val[N << 3] , d[N << 3] , deg[N << 3] , ls[N << 3] , rs[N << 3] ;
  int head[N << 3] , ecnt = 0 , rt , cnt = 0 ;
  bool vis[N << 3] ;
  void add(int u , int v , int w) { e[++ ecnt] = { v , head[u] , w } ; head[u] = ecnt ; deg[v] ++ ; }
  void build(int l , int r , int & p) {
    if(l == r) { p = l ; return ; }
    p = ++ cnt ; int mid = l + r >> 1 ;
    build(l , mid , ls[p]) ; build(mid + 1 , r , rs[p]) ;
    add(ls[p] , p , 0) ; add(rs[p] , p , 0) ;
  }
  void upd(int a , int b , int l , int r , int p , int to) {
    if(a <= l && r <= b) { add(p , to, 0) ; return ; }
    int mid = l + r >> 1 ;
    if(a <= mid) upd(a , b , l , mid , ls[p] , to) ;
    if(b > mid) upd(a , b , mid + 1 , r , rs[p] , to) ;
  }
  void topsort() {
    queue < int > q ;
    for(int i = 1 ; i <= cnt ; i ++) { if(! d[i]) d[i] = 1 ; if(! deg[i]) q.push(i) ; }
    while(q.size()) {
      int u = q.front() ; q.pop() ; vis[u] = 1 ;
      for(int i = head[u] ; i ; i = e[i].nxt) {
        int v = e[i].v ; cmax(d[v] , d[u] + e[i].w) ;
        if(val[v] && d[v] > val[v]) { cout << "NIE" << '\n' ; exit(0) ; }
        if(! -- deg[v]) q.push(v) ;
      }
    }
  }
  void main() {
    cin >> n >> s >> m ; cnt = n ; build(1 , n , rt) ;
    for(int i = 1 ; i <= s ; i ++) { int pos , _val ; cin >> pos >> _val ; d[pos] = val[pos] = _val ; }
    for(int i = 1 ; i <= m ; i ++) {
      int l , r , k ; cin >> l >> r >> k ;
      int pre = l - 1 , now = 0 ; ++ cnt ;
      while(k --) {
        cin >> now ;
        add(cnt , now , 1) ;
        if(now > pre + 1) upd(pre + 1 , now - 1 , 1 , n , rt , cnt) ;
        pre = now ;
      }
      if(now < r) upd(now + 1 , r , 1 , n , rt , cnt) ;
    }
    topsort() ;
    rep(i , 1 , cnt) if(! vis[i] || d[i] > limit) { cout << "NIE" << '\n' ; return ; }
    cout << "TAK" << '\n' ;
    rep(i , 1 , n) cout << d[i] << ' ' ;
  }
}
signed main() {
  _ios() ; ot() ;
  return stO_ATS_Orz :: main() , 0 ;
}
posted @ 2019-12-04 21:08  _Isaunoya  阅读(202)  评论(0编辑  收藏  举报