bzoj 3669: [Noi2014]魔法森林
用lct模拟一下过程2333,蒟蒻就不乱说了。。
1 #include<bits/stdc++.h> 2 #define N 200005 3 #define LL long long 4 #define inf 0x3f3f3f3f 5 #define ls c[x][0] 6 #define rs c[x][1] 7 using namespace std; 8 inline int ra() 9 { 10 int x=0,f=1; char ch=getchar(); 11 while (ch<'0' || ch>'9') {if (ch=='-') f=-1; ch=getchar();} 12 while (ch>='0' && ch<='9') {x=x*10+ch-'0'; ch=getchar();} 13 return x*f; 14 } 15 int top,q[200005]; 16 int n,m,ans=inf; 17 int mx[200005],val[200005]; 18 int father[200005],fa[200005],c[200005][2]; 19 bool rev[200005]; 20 struct node{int x,y,a,b;}e[100005]; 21 bool cmp(node a, node b){return a.a<b.a;} 22 int find(int x){return father[x]==x?x:father[x]=find(father[x]);} 23 void update(int x) 24 { 25 mx[x]=x; 26 if (val[mx[x]]<val[mx[ls]]) mx[x]=mx[ls]; 27 if (val[mx[x]]<val[mx[rs]]) mx[x]=mx[rs]; 28 } 29 bool isroot(int x){return c[fa[x]][0]!=x && c[fa[x]][1]!=x;} 30 bool lr(int x) {return c[fa[x]][1]==x;} 31 void pushdown(int x) 32 { 33 if (rev[x]) 34 { 35 rev[x]=0; rev[ls]^=1; rev[rs]^=1; 36 swap(ls,rs); 37 } 38 } 39 void rotate(int &x) 40 { 41 int y=fa[x],z=fa[y],l,r; bool nx=lr(x),ny=lr(y); 42 if (!isroot(y)) c[z][ny]=x; fa[x]=z; 43 c[y][nx]=c[x][!nx]; fa[c[x][!nx]]=y; 44 c[x][!nx]=y; fa[y]=x; update(y); update(x); 45 } 46 void splay(int &x) 47 { 48 top=0; q[++top]=x; 49 for (int i=x; !isroot(i); i=fa[i]) q[++top]=fa[i]; 50 while (top) pushdown(q[top--]); 51 while (!isroot(x)) 52 { 53 int y=fa[x],z=fa[y]; 54 if (!isroot(y)) 55 { 56 if (lr(x)==lr(y)) rotate(y); 57 else rotate(x); 58 } 59 rotate(x); 60 } 61 } 62 void access(int x) 63 { 64 for (int t=0; x; t=x, x=fa[x]) 65 splay(x),c[x][1]=t,update(x); 66 } 67 void makeroot(int x) 68 { 69 access(x); splay(x); rev[x]^=1; 70 } 71 void link(int x, int y) 72 { 73 makeroot(x); fa[x]=y; 74 } 75 void cut(int x, int y) 76 { 77 makeroot(x); access(y); splay(y); 78 c[y][0]=fa[x]=0; update(y); 79 } 80 int query(int x, int y) 81 { 82 makeroot(x); access(y); splay(y); 83 return mx[y]; 84 } 85 int main() 86 { 87 n=ra(); m=ra(); 88 for (int i=1; i<=n; i++) father[i]=i; 89 for (int i=1; i<=m; i++) 90 e[i].x=ra(),e[i].y=ra(),e[i].a=ra(),e[i].b=ra(); 91 sort(e+1,e+m+1,cmp); int tot=0; 92 for (int i=1; i<=m; i++) 93 { 94 int x=e[i].x,y=e[i].y,a=e[i].a,b=e[i].b; 95 if (find(x)==find(y)) 96 { 97 int t=query(x,y); 98 if (val[t]>e[i].b) 99 { 100 cut(t,e[t-n].x); 101 cut(t,e[t-n].y); 102 } 103 else 104 { 105 if (find(1)==find(n)) ans=min(ans,e[i].a+val[query(1,n)]); 106 continue; 107 } 108 } 109 else father[find(x)]=find(y); 110 val[n+i]=e[i].b; mx[n+i]=n+i; 111 link(x,n+i); link(y,n+i); 112 if (find(1)==find(n)) ans=min(ans,e[i].a+val[query(1,n)]); 113 } 114 if (ans==inf) puts("-1"); 115 else cout<<ans; 116 return 0; 117 }