好屎的一道题啊
倒序加边kruscal,LCT维护maxn
然而我在bzoj上并卡不过去
操
放上我用尽心思卡评测的代码
1 #pragma optimize GCC ("O3") 2 #include<cstdio> 3 #include<algorithm> 4 #include<map> 5 #define N 1000500 6 #define pp pair<int,int> 7 #define mp make_pair 8 #define inf 0x7fffffff 9 using namespace std; 10 char xch,xB[1<<15],*xS=xB,*xTT=xB; 11 #define getc() (xS==xTT&&(xTT=(xS=xB)+fread(xB,1,1<<15,stdin),xS==xTT)?0:*xS++) 12 inline int getint() 13 { 14 int x=0,f=1;char ch=getc(); 15 while(ch<‘0‘|ch>‘9‘){if(ch==‘-‘)f=-1;ch=getc();} 16 while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getc();} 17 return x*f; 18 } 19 int n,m,q; 20 map<pp,int> mm; 21 struct Node{ 22 Node *ch[2],*fa; 23 int val,maxn,maxid,id,rev; 24 Node(); 25 void Rev(); 26 void pushup(); 27 void pushdown(); 28 }*null=new Node,tree[1110000]; 29 Node :: Node(){ 30 ch[0]=ch[1]=fa=null; 31 val=maxn=-inf;id=rev=maxid=0; 32 } 33 void Node :: Rev(){ 34 rev^=1; 35 swap(ch[0],ch[1]); 36 } 37 void Node :: pushup(){ 38 if(id>n)maxn=val,maxid=id; 39 else maxn=-inf,maxid=0; 40 if(ch[0]->maxn>maxn){ 41 maxn=ch[0]->maxn; 42 maxid=ch[0]->maxid; 43 } 44 if(ch[1]->maxn>maxn){ 45 maxn=ch[1]->maxn; 46 maxid=ch[1]->maxid; 47 } 48 } 49 void Node :: pushdown(){ 50 if(rev){ 51 ch[0]->Rev(); 52 ch[1]->Rev(); 53 rev=0; 54 } 55 } 56 void rotate(Node *x){ 57 Node *y=x->fa,*z=y->fa; 58 int w=y->ch[1]==x; 59 y->ch[w]=x->ch[w^1];x->ch[w^1]->fa=y; 60 x->ch[w^1]=y;y->fa=x; 61 if(z->ch[0]==y)z->ch[0]=x; 62 if(z->ch[1]==y)z->ch[1]=x; 63 x->fa=z; 64 y->pushup();x->pushup(); 65 } 66 bool isroot(Node *x){ 67 return (x->fa->ch[0]!=x)&&(x->fa->ch[1]!=x); 68 } 69 void splay(Node *x){ 70 Node *y,*z; 71 x->pushdown(); 72 while(!isroot(x)){ 73 y=x->fa;z=y->fa; 74 z->pushdown();y->pushdown();x->pushdown(); 75 if(((z->ch[0]==y)&&(y->ch[0]==x))||((z->ch[1]==y)&&(y->ch[1]==x))) 76 rotate(y); 77 rotate(x); 78 } 79 } 80 void access(Node *x){ 81 Node *y=null; 82 while(x!=null){ 83 splay(x); 84 x->ch[1]=y; 85 x->pushup(); 86 y=x;x=x->fa; 87 } 88 } 89 void make_root(Node *x){ 90 access(x); 91 splay(x); 92 x->Rev(); 93 } 94 void link(Node *x,Node *y){ 95 make_root(x); 96 x->fa=y; 97 } 98 void cut(Node *x,Node *y){ 99 make_root(x); 100 access(y);splay(y); 101 y->ch[0]=x->fa=null; 102 y->pushup(); 103 } 104 pp query(Node *x,Node *y){ 105 make_root(x); 106 access(y);splay(y); 107 return mp(y->maxn,y->maxid); 108 } 109 struct edge{ 110 int u,v,w; 111 }ed[N]; 112 struct data{ 113 int o,x,y,id,ans; 114 }d[N]; 115 bool vis[N]; 116 int fa[100005]; 117 int find(int x){ 118 return x==fa[x]?x:fa[x]=find(fa[x]); 119 } 120 int main(){ 121 null->ch[0]=null->ch[1]=null->fa=null; 122 n=getint();m=getint();q=getint(); 123 for(int i=1,u,v,w;i<=m;i++){ 124 u=getint();v=getint();w=getint(); 125 if(u>v)swap(u,v); 126 mm[mp(u,v)]=i; 127 ed[i].u=u;ed[i].v=v;ed[i].w=w; 128 tree[n+i].val=tree[n+i].maxn=w; 129 tree[n+i].id=tree[n+i].maxid=n+i; 130 } 131 for(int i=1;i<=q;i++){ 132 d[i].o=getint();d[i].x=getint();d[i].y=getint(); 133 if(d[i].x>d[i].y)swap(d[i].x,d[i].y); 134 if(d[i].o==2) 135 d[i].id=mm[mp(d[i].x,d[i].y)], 136 vis[d[i].id]=1; 137 } 138 for(int i=1;i<=n;i++){ 139 tree[i].id=i; 140 fa[i]=i; 141 } 142 for(int i=1;i<=m;i++)if(!vis[i]){ 143 if(find(ed[i].u)==find(ed[i].v)){ 144 pp x=query(&tree[ed[i].u],&tree[ed[i].v]); 145 if(x.first>ed[i].w){ 146 cut(&tree[x.second],&tree[ed[x.second-n].u]); 147 cut(&tree[x.second],&tree[ed[x.second-n].v]); 148 link(&tree[n+i],&tree[ed[i].u]); 149 link(&tree[n+i],&tree[ed[i].v]); 150 } 151 } 152 else{ 153 link(&tree[n+i],&tree[ed[i].u]); 154 link(&tree[n+i],&tree[ed[i].v]); 155 fa[find(ed[i].u)]=find(ed[i].v); 156 } 157 } 158 for(int i=q;i;i--){ 159 if(d[i].o&1) 160 d[i].ans=query(&tree[d[i].x],&tree[d[i].y]).first; 161 else{ 162 pp x=query(&tree[d[i].x],&tree[d[i].y]); 163 if(x.first>ed[d[i].id].w){ 164 cut(&tree[x.second],&tree[ed[x.second-n].u]); 165 cut(&tree[x.second],&tree[ed[x.second-n].v]); 166 link(&tree[n+d[i].id],&tree[d[i].x]); 167 link(&tree[n+d[i].id],&tree[d[i].y]); 168 } 169 } 170 } 171 for(int i=1;i<=q;i++)if(d[i].o&1) 172 printf("%d\n",d[i].ans); 173 return 0; 174 }