# bzoj4025 二分图

【题解】

# include <stdio.h>
# include <string.h>
# include <iostream>
# include <algorithm>
// # include <bits/stdc++.h>

using namespace std;

typedef long long ll;
typedef long double ld;
typedef unsigned long long ull;
const int M = 5e5 + 10, N = 1e6 + 10;
const int mod = 1e9+7;

# define RG register
# define ST static

int n, m, T;

struct edge {
int u, v, st, ed;
edge() {}
edge(int u, int v, int st, int ed) : u(u), v(v), st(st), ed(ed) {}
}e[M];

int st[N];
int stn = 0;

struct us {
int n, fa[M], rk[M], dis[M];
inline void set(int _n) {
n = _n;
for (int i=1; i<=n; ++i) fa[i] = i, rk[i] = 1, dis[i] = 0;
}
inline int getf(int x) {
return fa[x] == x ? x : getf(fa[x]);
}
inline int getdis(int x) {
int d = 0;
while(fa[x] != x) d += dis[x], x = fa[x];
return d;
}
inline void un(int fu, int fv, int d) {
if(rk[fu] > rk[fv]) swap(fu, fv);
if(rk[fu] == rk[fv]) rk[fv] ++, st[++stn] = -fv;
fa[fu] = fv;
dis[fu] = d;
++stn;
st[stn] = fu;
}
inline void re() {
int x = st[stn]; --stn;
if(x < 0) --rk[-x];
else dis[x] = 0, fa[x] = x;
}
}E;

bool ans[M];

inline void solve(int tl, int tr, int er) {
//    printf("l = %d, r = %d\n", tl, tr);
int cur_stn = stn;
for (int i=1; i<=er; ++i) {
if(!(e[i].st <= tl && tr <= e[i].ed)) continue;
//        printf("doing: (%d, %d, %d, %d)\n", e[i].u, e[i].v, e[i].st, e[i].ed);
int fu = E.getf(e[i].u), fv = E.getf(e[i].v);
int du = E.getdis(e[i].u), dv = E.getdis(e[i].v);
if(fu != fv) E.un(fu, fv, du+dv+1);
else {
//            printf("%d %d fa = %d %d %d\n", e[i].u, e[i].v, E.fa[1], du, dv);
if((du+dv+1)&1) {
//                puts("Proves odd");
while(stn != cur_stn) E.re();
return ;
}
}
swap(e[i], e[er]); --er; --i;
}
if(tl == tr) {
ans[tl] = 1;
while(stn != cur_stn) E.re();
return ;
}
int mid = tl+tr >> 1;
int ER = er;
for (int i=1; i<=er; ++i)
if(e[i].st > mid) {
swap(e[i], e[er]);
--er; --i;
}
solve(tl, mid, er);
er = ER;
for (int i=1; i<=er; ++i) {
if(e[i].ed <= mid) {
swap(e[i], e[er]);
--er; --i;
}
}
solve(mid+1, tr, er);
while(stn != cur_stn) E.re();
}

int main() {
cin >> n >> m >> T;
E.set(n);
int en = 0;
for (int i=1, u, v, sta, end; i<=m; ++i) {
scanf("%d%d%d%d", &u, &v, &sta, &end);
++sta; if(sta>end) continue;
e[++en] = edge(u, v, sta, end);
}
m = en;
solve(1, T, m);
for (int i=1; i<=T; ++i) puts(ans[i] ? "Yes" : "No");
return 0;
}
View Code

posted @ 2017-06-02 23:05  Galaxies  阅读(115)  评论(0编辑  收藏  举报