题解
- 首先,我们先将边打进队列里
- 那么,就可以一波bfs,做并查集,求出深度,位于哪条边
- 然后,就比较暴力了
- 读入,如果为"1",那就一直往上跑,找到第一条出现的黑边
- 如果为"2",现将路径一直往上条,沿路都为黑边
代码
1 #include<cstdio>
2 #include<iostream>
3 using namespace std;
4 int n,m,x,y,z,tot,head,tail,ans,w[2000001],state[2000001],visit[2000001],deep[2000001],k[2000001],next[2000001],v[2000001],to[2000001],last[2000001],fa[2000001];
5 void insert(int x,int y,int z)
6 {
7 next[++tot]=y;
8 v[tot]=z;
9 to[tot]=last[x];
10 last[x]=tot;
11 }
12 int main()
13 {
14 scanf("%d%d",&n,&m);
15 for (int i=1;i<=n-1;i++)
16 {
17 scanf("%d%d",&x,&y);
18 insert(x,y,i); insert(y,x,i);
19 }
20 head=0; tail=1; state[1]=1; visit[1]=1; deep[1]=1;
21 while (head<tail)
22 {
23 head++; x=state[head];
24 for (int i=last[x];i;i=to[i])
25 {
26 y=next[i];
27 if (visit[y]==0)
28 {
29 fa[y]=x;
30 deep[y]=deep[x]+1;
31 k[y]=v[i];
32 visit[y]=1;
33 tail++;
34 state[tail]=y;
35 }
36 }
37 }
38 for (int i=1;i<=m;i++)
39 {
40 scanf("%d%d",&x,&y);
41 if (x==2)
42 {
43 scanf("%d",&z);
44 if (deep[y]<deep[z]) swap(z,y);
45 while (deep[y]>deep[z]) w[y]=1,y=fa[y];
46 while (y!=z)
47 {
48 w[y]=w[z]=1;
49 y=fa[y];
50 z=fa[z];
51 }
52 }
53 else
54 {
55 ans=0;
56 while (y!=0)
57 {
58 if (w[y]==1) { ans=k[y]; break; }
59 y=fa[y];
60 }
61 printf("%d
",ans);
62 }
63 }
64 return 0;
65 }