离线处理后不难发现就是一个LCT询问两点间最大值最小值之类的,然后就上模板
#include <iostream>
#include <algorithm>
#include <cstdio>
#include <cstring>
#include <cmath>
using namespace std;
int getint()
{
char ch = getchar();
for ( ; ch > '9' || ch < '0'; ch = getchar());
int tmp = 0;
for ( ; '0' <= ch && ch <= '9'; ch = getchar())
tmp = tmp * 10 + ch-'0';
return tmp;
}
int n,m,Q,top;
int f[1500005];
int fa[1500005],tr[1500005][2],s[1500005];
int mx[1500005],val[1500005];
bool rev[1500005];
struct edge{int u,v,w,id;bool d;}e[1000005];
struct que{int f,x,y,ans,id;}q[100005];
bool cmp(edge a,edge b)
{
return a.w<b.w;
}
bool cmp2(edge a,edge b)
{
return a.id<b.id;
}
bool operator<(edge a,edge b)
{
return a.u<b.u||(a.u==b.u&&a.v<b.v);
}
int getf(int x){return x==f[x]?x:f[x]=getf(f[x]);}
bool isroot(int x)
{
return (tr[fa[x]][0]!=x)&&(tr[fa[x]][1]!=x);
}
void pushup(int x)
{
int l=tr[x][0],r=tr[x][1];
mx[x]=x;
if(val[mx[l]]>val[mx[x]])mx[x]=mx[l];
if(val[mx[r]]>val[mx[x]])mx[x]=mx[r];
}
void rotate(int x)
{
int y=fa[x],z=fa[y],l,r;
if(tr[y][0]==x)l=0;else l=1;r=l^1;
if(!isroot(y))
{
if(tr[z][0]==y)tr[z][0]=x;
else tr[z][1]=x;
}
fa[x]=z;fa[y]=x;fa[tr[x][r]]=y;
tr[y][l]=tr[x][r];tr[x][r]=y;
pushup(y);pushup(x);
}
int get(int u,int v)
{
int l=1,r=m;
while(l<=r)
{
int mid=(l+r)>>1;
if(e[mid].u<u||(e[mid].u==u&&e[mid].v<v))l=mid+1;
else if(e[mid].u==u&&e[mid].v==v)return mid;
else r=mid-1;
}
}
void pushdown(int x)
{
if(!isroot(x))
pushdown(fa[x]);
int l=tr[x][0],r=tr[x][1];
if(rev[x])
{
rev[x]^=1;rev[l]^=1;rev[r]^=1;
swap(tr[x][0],tr[x][1]);
}
}
void splay(int x)
{
pushdown(x);
int y,z;
while(!isroot(x))
{
y=fa[x];z=fa[x];
if(!isroot(y))
{
if((tr[y][0]==x)^(tr[z][0]==y)) rotate(x);
else rotate(y);
}
rotate(x);
}
}
void access(int x)
{
int t=0;
while(x)
{
splay(x);tr[x][1]=t;
pushup(x);
t=x;x=fa[x];
}
}
void makeroot(int x)
{
access(x);splay(x);rev[x]^=1;
}
void link(int x,int y)
{
makeroot(x);fa[x]=y;
}
void cut(int x,int y)
{
makeroot(x);access(y);splay(y);tr[y][0]=fa[x]=0;
}
int query(int x,int y)
{
makeroot(x);access(y);splay(y);return mx[y];
}
int main()
{
n=getint();m=getint();Q=getint();
for(int i=1;i<=n;i++)f[i]=i;
for(int i=1;i<=m;i++)
{
e[i].u=getint(),e[i].v=getint(),e[i].w=getint();
if(e[i].u>e[i].v)swap(e[i].u,e[i].v);
}
sort(e+1,e+m+1,cmp);
for(int i=1;i<=m;i++)
{
e[i].id=i;
val[n+i]=e[i].w;
mx[n+i]=n+i;
}
sort(e+1,e+m+1);
for(int i=1;i<=Q;i++)
{
q[i].f=getint();
q[i].x=getint(),q[i].y=getint();
if(q[i].f==2)
{
if(q[i].x>q[i].y)swap(q[i].x,q[i].y);
int t=get(q[i].x,q[i].y);
e[t].d=1;q[i].id=e[t].id;
}
}
sort(e+1,e+m+1,cmp2);
int tot=0;
for(int i=1;i<=m;i++)
if(!e[i].d)
{
int u=e[i].u,v=e[i].v,x=getf(u),y=getf(v);
if(x!=y)
{
f[x]=y;
link(u,i+n);link(v,i+n);
tot++;
if(tot==n-1)break;
}
}
for(int i=Q;i;i--)
{
if(q[i].f==1)
q[i].ans=val[query(q[i].x,q[i].y)];
else
{
int u=q[i].x,v=q[i].y,k=q[i].id;
int t=query(u,v);
if(e[k].w<val[t])
{
cut(e[t-n].u,t);cut(e[t-n].v,t);
link(u,k+n);link(v,k+n);
}
}
}
for(int i=1;i<=Q;i++)
if(q[i].f==1)printf("%d\n",q[i].ans);
return 0;
}