RT,刚学线段树分治,太菜了不会带撤销DSU,于是用LCT实现DSU的功能,现在RE30分。
#include <stack>
#include <vector>
#include <cstdio>
#include <utility>
#include <cstring>
#include <algorithm>
using namespace std;
#define il inline
#define re register
#define mp(x,y) make_pair(x,y)
typedef pair<int,int> Pair;
const int N=1e6+10;
namespace FastIO
{
char buf[1<<21],buf2[1<<21],*p1=buf,*p2=buf;
int p,p3=-1;
il int getc(){return p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++;}
il void flush(){fwrite(buf2,1,p3+1,stdout),p3=-1;}
#define isdigit(ch) (ch>=48&&ch<=57)
template <typename T>
il void read(T &x)
{
re bool f=0;x=0;
re char ch=getc();
while(!isdigit(ch)) f|=(ch=='-'),ch=getc();
while(isdigit(ch)) x=(x<<1)+(x<<3)+(ch^48),ch=getc();
x=f?-x:x;
}
template <typename T>
il void print(T x)
{
if(p3>(1<<20)) flush();
if(x<0) buf2[++p3]=45,x=-x;
re int a[50]={};
do{a[++p]=x%10+48;}while(x/=10);
do{buf2[++p3]=a[p];}while(--p);
}
}
using namespace FastIO;
struct Link_Cut_Tree
{
int fa[N<<1],son[2][N<<1],tag[N<<1];
il void init()
{
memset(fa,0,sizeof(fa));
memset(son,0,sizeof(son));
memset(tag,0,sizeof(tag));
return;
}
#define ls(x) (son[0][x])
#define rs(x) (son[1][x])
#define indent(x) (rs(fa[x])==x)
#define notrt(x) (ls(fa[x])==x||rs(fa[x])==x)
#define connect(x,f,s) (son[s][f]=x,fa[x]=f)
#define reverse(x) (swap(ls(x),rs(x)),tag[x]^=1)
il void pushdown(int x)
{
if(!tag[x]) return;
if(ls(x)) reverse(ls(x));
if(rs(x)) reverse(rs(x));
tag[x]^=1;return;
}
il void rotate(int x)
{
re int f=fa[x],ff=fa[f],k=indent(x);
connect(son[k^1][x],f,k);
fa[x]=ff;
if(notrt(f)) son[indent(f)][ff]=x;
connect(f,x,k^1);return;
}
int st[N<<2],top;
il void pushall(int x)
{
top=0;
while(notrt(x)) st[++top]=x,x=fa[x];
pushdown(x);
while(top) pushdown(st[top--]);
return;
}
il void splay(int x)
{
pushall(x);
re int f,ff;
while(notrt(x))
{
f=fa[x];ff=fa[f];
if(notrt(f)) rotate(indent(x)^indent(f)?x:f);
rotate(x);
}
return;
}
il void access(int x)
{
for(re int i=0;x;x=fa[i=x])
splay(x),rs(x)=i;
return;
}
#define makert(x) (access(x),splay(x),reverse(x))
il int getrt(int x)
{
access(x);splay(x);
while(ls(x)) pushdown(x),x=ls(x);
splay(x);return x;
}
il void link(int x,int y){makert(x);fa[x]=y;return;}
il void cut(int x,int y){makert(x);fa[y]=rs(x)=0;return;}
}LCT;
int n,m,k;
vector<Pair>lz[N<<2];
il void change(int p,int l,int r,int L,int R,int x,int y)
{
if(l>R||r<L) return;
if(l>=L&&r<=R){lz[p].push_back(mp(x,y));return;}
re int mid=(l+r)>>1;
change(p<<1,l,mid,L,R,x,y);
change(p<<1|1,mid+1,r,L,R,x,y);
return;
}
stack<Pair>st;
int top;
il void merge(int x,int y)
{
re int fx=LCT.getrt(x);
re int fy=LCT.getrt(y);
st.push(mp(fx,fy));++top;
LCT.link(fx,fy);return;
}
il void solve(int p,int l,int r)
{
re int flag=1,lst=top;
for(re int i=0,a,b;i<lz[p].size();++i)
{
a=LCT.getrt(lz[p][i].first);
b=LCT.getrt(lz[p][i].second);
if(a==b)
{
for(re int j=l;j<=r;++j) puts("No");
flag=0;break;
}
merge(lz[p][i].first,lz[p][i].second+n);
merge(lz[p][i].second,lz[p][i].first+n);
}
if(flag)
{
if(l==r) puts("Yes");
else
{
re int mid=(l+r)>>1;
solve(p<<1,l,mid);
solve(p<<1|1,mid+1,r);
}
}
while(top>lst)
{
LCT.cut(st.top().first,st.top().second);
st.pop();--top;
}
return;
}
int main()
{
read(n),read(m),read(k);LCT.init();
for(re int i=1,x,y,l,r;i<=m;++i)
{
read(x),read(y),read(l),read(r);
change(1,1,k,l+1,r,x,y);
}
solve(1,1,k);return 0;
}