• BZOJ4025 二分图


    首先对时间分治,每个节点表示一个时间的区间$[l, r]$

    然后对于每个节点记录一个可以撤销的并查集,维护图的信息即可

    (这里的并查集不用路径压缩,只要按秩合并,这样子可以保证单次操作的时间复杂度是$O(logn)$的)

    我去啊。。。把边分类这一段代码调的我QAQ了。。。代码能力太弱QAQQQ

      1 /**************************************************************
      2     Problem: 4025
      3     User: rausen
      4     Language: C++
      5     Result: Accepted
      6     Time:4344 ms
      7     Memory:6668 kb
      8 ****************************************************************/
      9  
     10 #include <cstdio>
     11 #include <algorithm>
     12  
     13 using namespace std;
     14 const int N = 1e5 + 5;
     15 const int M = 2e5 + 5;
     16  
     17 inline int read();
     18  
     19 struct edge {
     20     int x, y, st, ed;
     21  
     22     inline void get() {
     23         x = read(), y = read();
     24         st = read() + 1, ed = read();
     25     }
     26 } e[M];
     27  
     28 int n, m, time;
     29  
     30 namespace set {
     31     int fa[N], d[N], a[N];
     32     int s[N << 2], top = 0;
     33      
     34     int find(int x) {
     35         while (fa[x] != x) x = fa[x];
     36         return x;
     37     }
     38     int dep(int x) {
     39         static int res;
     40         for (res = 0; fa[x] != x; x = fa[x])
     41             res ^= a[x];
     42         return res;
     43     }
     44      
     45     void set_union(int x, int y, int _d) {
     46         if (d[x] > d[y]) swap(x, y);
     47         if (d[x] == d[y]) ++d[y], s[++top] = -y;
     48         fa[x] = y, a[x] = _d, s[++top] = x; 
     49     }
     50      
     51     void set_resume(int t) {
     52         for (; top != t; --top)
     53             if (s[top] < 0) --d[-s[top]];
     54             else fa[s[top]] = s[top], a[s[top]] = 0;
     55     }
     56 }
     57 using namespace set;
     58  
     59 void work(int l, int r, int m) {
     60     int mid = l + r >> 1, now = top;
     61     int i, j, fx, fy, _d;
     62     for (i = 1; i <= m; ++i)
     63         if (e[i].st <= l && r <= e[i].ed) {
     64             fx = find(e[i].x), fy = find(e[i].y), _d = !(dep(e[i].x) ^ dep(e[i].y));
     65             if (fx != fy) set_union(fx, fy, _d);
     66             else if (_d) {
     67                 while (l <= r)
     68                     puts("No"), ++l;
     69                 set_resume(now);
     70                 return;
     71             }
     72             swap(e[m--], e[i--]);
     73         };
     74     if (l == r) puts("Yes");
     75     else {
     76         for (i = 1, j = m; i <= j; ++i)
     77             if (e[i].st > mid) swap(e[j--], e[i--]);
     78         work(l, mid, j);
     79         for (i = 1, j = m; i <= j; ++i)
     80             if (e[i].ed <= mid) swap(e[j--], e[i--]);
     81         work(mid + 1, r, j);
     82     }
     83     set_resume(now);
     84 }
     85  
     86 int main() {
     87     int i;
     88     n = read(), m = read(), time = read();
     89     for (i = 1; i <= n; ++i)
     90         fa[i] = i, d[i] = 1, a[i] = 0;
     91     for (i = 1; i <= m; ++i) e[i].get();
     92     for (i = 1; i <= m; ++i)
     93         if (e[i].st > e[i].ed) swap(e[i--], e[m--]);
     94     work(1, time, m);
     95     return 0;
     96 }
     97  
     98 inline int read() {
     99     static int x, sgn;
    100     static char ch;
    101     x = 0, sgn = 1, ch = getchar();
    102     while (ch < '0' || '9' < ch) {
    103         if (ch == '-') sgn = -1;
    104         ch = getchar();
    105     }
    106     while ('0' <= ch && ch <= '9') {
    107         x = x * 10 + ch - '0';
    108         ch = getchar();
    109     }
    110     return sgn * x;
    111 }
    View Code
  • 相关阅读:
    JS OOP -03 JS类的实现
    python 配置文件__ConfigParser
    1103_ddt 数据处理
    1101_数据处理优化
    了解 ptyhon垃圾回收机制
    10_30_unittest
    10_27_unittest
    10_27_requests模块
    知识积累 哈。。。
    Python练习
  • 原文地址:https://www.cnblogs.com/rausen/p/4502032.html
Copyright © 2020-2023  润新知