1 #include<iostream>
2 #include<cstdio>
3 #include<algorithm>
4 #include<cstring>
5 using namespace std;
6 struct Node
7 {
8 int next,to,dis;
9 }edge[400001];
10 int f[200001][3],num,head[200001],n,ans;
11 void add(int u,int v,int dis)
12 {
13 num++;
14 edge[num].next=head[u];
15 head[u]=num;
16 edge[num].to=v;
17 edge[num].dis=dis;
18 }
19 int gcd(int a,int b)
20 {
21 if (b==0) return a;
22 return gcd(b,a%b);
23 }
24 void dfs_dp(int x,int pa)
25 {int i;
26 for (i=head[x]; i; i=edge[i].next)
27 {
28 int v=edge[i].to;
29 if (v==pa) continue;
30 dfs_dp(v,x);
31 int flag[3]={0};
32 flag[(edge[i].dis)%3]=f[v][0];
33 flag[(1+edge[i].dis)%3]=f[v][1];
34 flag[(2+edge[i].dis)%3]=f[v][2];
35 ans+=flag[0]*f[x][0]+flag[1]*f[x][2]+flag[2]*f[x][1];
36 f[x][0]+=flag[0];
37 f[x][1]+=flag[1];
38 f[x][2]+=flag[2];
39 }
40 ans+=f[x][0];
41 f[x][0]++;
42 }
43 int main()
44 {int i,u,v,d;
45 cin>>n;
46 for (i=1; i<=n-1; i++)
47 {
48 scanf("%d%d%d",&u,&v,&d);
49 add(u,v,d);
50 add(v,u,d);
51 }
52 dfs_dp(1,0);
53 d=gcd(ans*2+n,n*n);
54 printf("%d/%d",(ans*2+n)/d,n*n/d);
55 }
1 #include<iostream>
2 #include<cstdio>
3 #include<algorithm>
4 #include<cstring>
5 using namespace std;
6 struct Node
7 {
8 int next,to,dis;
9 }edge[400001];
10 int num,head[200001],f[200001][3],ans,k;
11 int size[200001],maxsize[200001],minsize,root,n;
12 bool vis[200001];
13 void add(int u,int v,int dis)
14 {
15 num++;
16 edge[num].next=head[u];
17 head[u]=num;
18 edge[num].to=v;
19 edge[num].dis=dis;
20 }
21 int gcd(int a,int b)
22 {
23 if (b==0) return a;
24 return gcd(b,a%b);
25 }
26 void get_size(int x,int fa)
27 {
28 int i;
29 size[x]=1;
30 maxsize[x]=0;
31 for (i=head[x]; i; i=edge[i].next)
32 {
33 int v=edge[i].to;
34 if (vis[v]==0&&v!=fa)
35 {
36 get_size(v,x);
37 size[x]+=size[v];
38 maxsize[x]=max(maxsize[x],size[v]);
39 }
40 }
41 }
42 void get_root(int r,int x,int fa)
43 {
44 int i;
45 maxsize[x]=max(maxsize[x],size[r]-size[x]);
46 if (maxsize[x]<minsize)
47 {
48 root=x;
49 minsize=maxsize[x];
50 }
51 for (i=head[x]; i; i=edge[i].next)
52 {
53 int v=edge[i].to;
54 if (vis[v]==0&&v!=fa)
55 {
56 get_root(r,v,x);
57 }
58 }
59 }
60 void get_ans(int x,int fa)
61 {
62 int i;
63 f[x][0]=1;
64 f[x][1]=f[x][2]=0;
65 for (i=head[x]; i; i=edge[i].next)
66 {
67 int v=edge[i].to;
68 if (vis[v]==0&&v!=fa)
69 {
70 get_ans(v,x);
71 f[x][edge[i].dis%3] += f[edge[i].to][0];
72 f[x][(1+edge[i].dis)%3] += f[edge[i].to][1];
73 f[x][(2+edge[i].dis)%3] += f[edge[i].to][2];
74 }
75 }
76 }
77 void solve(int x)
78 {
79 int i;
80 minsize=2e9;
81 get_size(x,0);
82 get_root(x,x,0);
83 vis[root]=1;
84 f[root][0]=1;
85 f[root][1]=f[root][2]=0;
86 for (i=head[root]; i; i=edge[i].next)
87 {
88 int v=edge[i].to;
89 if (vis[v]==0)
90 {
91 get_ans(v,root);
92 int flag[3]={0};
93 flag[(edge[i].dis)%3]=f[v][0];
94 flag[(1+edge[i].dis)%3]=f[v][1];
95 flag[(2+edge[i].dis)%3]=f[v][2];
96 ans+=flag[0]*f[root][0]+flag[1]*f[root][2]+flag[2]*f[root][1];
97 f[root][0]+=flag[0];
98 f[root][1]+=flag[1];
99 f[root][2]+=flag[2];
100 }
101 }
102 for (i=head[root]; i; i=edge[i].next)
103 {
104 int v=edge[i].to;
105 if (vis[v]==0)
106 {
107 solve(v);
108 }
109 }
110 }
111 int main()
112 {int i,u,v,d;
113 cin>>n;
114 for (i=1; i<=n-1; i++)
115 {
116 scanf("%d%d%d",&u,&v,&d);
117 add(u,v,d);
118 add(v,u,d);
119 }
120 solve(1);
121 d=gcd(ans*2+n,n*n);
122 printf("%d/%d",(ans*2+n)/d,n*n/d);
123 }