POJ - 1741 Tree

Description
Give a tree with n vertices,each edge has a length(positive integer less than 1001).
Define dist(u,v)=The min distance between node u and v.
Give an integer k,for every pair (u,v) of vertices is called valid if and only if dist(u,v) not exceed k.
Write a program that will count how many pairs which are valid for a given tree.

Input
The input contains several test cases. The first line of each test case contains two integers n, k. (n<=10000) The following n-1 lines each contains three integers u,v,l, which means there is an edge between node u and v of length l.
The last test case is followed by two zeros.

Output
For each test case output the answer on a single line.

Sample Input

5 4
1 2 3
1 3 1
1 4 2
3 5 1
0 0

Sample Output

8

 

题目大意:求树上距离小于k的点对个数

裸题,树的点分治

  1 const

  2     maxn=10010;

  3 var

  4     n,k,cut,cuts,ans,num,tot:longint;

  5     next,last,w:array[0..maxn*2]of longint;

  6     first,size,a:array[0..maxn]of longint;

  7     flag:array[0..maxn]of boolean;

  8 

  9 function max(x,y:longint):longint;

 10 begin

 11     if x>y then exit(x);

 12     exit(y);

 13 end;

 14 

 15 procedure dfs1(x:longint);

 16 var

 17     i,s:longint;

 18 begin

 19     size[x]:=1;

 20     i:=first[x];

 21     flag[x]:=false;

 22     s:=0;

 23     while i<>0 do

 24       begin

 25         if flag[last[i]] then

 26         begin

 27           dfs1(last[i]);

 28           inc(size[x],size[last[i]]);

 29           s:=max(s,size[last[i]]);

 30         end;

 31         i:=next[i];

 32       end;

 33     if max(num-size[x],s)<cuts then

 34     begin

 35       cut:=x;

 36       cuts:=max(num-size[x],s);

 37     end;

 38     flag[x]:=true;

 39 end;

 40 

 41 procedure swap(var x,y:longint);

 42 var

 43     t:longint;

 44 begin

 45     t:=x;x:=y;y:=t;

 46 end;

 47 

 48 procedure sort(l,r:longint);

 49 var

 50     i,j,y:longint;

 51 begin

 52     i:=l;

 53     j:=r;

 54     y:=a[(l+r)>>1];

 55     repeat

 56       while a[i]<y do

 57         inc(i);

 58       while a[j]>y do

 59         dec(j);

 60       if i<=j then

 61       begin

 62         swap(a[i],a[j]);

 63         inc(i);

 64         dec(j);

 65       end;

 66     until i>j;

 67     if i<r then sort(i,r);

 68     if j>l then sort(l,j);

 69 end;

 70 

 71 procedure dfs2(x,d:longint);

 72 var

 73     i:longint;

 74 begin

 75     inc(a[0]);

 76     a[a[0]]:=d;

 77     flag[x]:=false;

 78     i:=first[x];

 79     while i<>0 do

 80       begin

 81         if flag[last[i]] then dfs2(last[i],d+w[i]);

 82         i:=next[i];

 83       end;

 84     flag[x]:=true;

 85 end;

 86 

 87 function calc(x,d:longint):longint;

 88 var

 89     l,r:longint;

 90 begin

 91     calc:=0;

 92     a[0]:=0;

 93     dfs2(x,d);

 94     sort(1,a[0]);

 95     l:=a[0];

 96     for r:=1 to a[0] do

 97       begin

 98         while (a[l]+a[r]>k) and (l>0) do

 99           dec(l);

100         if l<r then inc(calc,l)

101         else inc(calc,r-1);

102       end;

103 end;

104 

105 procedure work;

106 var

107     i:longint;

108 begin

109     inc(ans,calc(cut,0));

110     flag[cut]:=false;

111     i:=first[cut];

112     while i<>0 do

113       begin

114         if flag[last[i]] then dec(ans,calc(last[i],w[i]));

115         i:=next[i];

116       end;

117     i:=first[cut];

118     while i<>0 do

119       begin

120         if flag[last[i]] then

121         begin

122           dfs1(last[i]);

123           num:=last[i];

124           cuts:=num;

125           cut:=last[i];

126           dfs1(last[i]);

127           work;

128         end;

129         i:=next[i];

130       end;

131 end;

132 

133 procedure insert(x,y,z:longint);

134 begin

135     inc(tot);

136     last[tot]:=y;

137     next[tot]:=first[x];

138     first[x]:=tot;

139     w[tot]:=z;

140 end;

141 

142 procedure init;

143 var

144     i,x,y,z:longint;

145 begin

146     read(n,k);

147     if n=0 then halt;

148     tot:=0;

149     for i:=1 to n do

150       begin

151         first[i]:=0;

152         flag[i]:=true;

153       end;

154     ans:=0;

155     for i:=1 to n-1 do

156       begin

157         read(x,y,z);

158         insert(x,y,z);

159         insert(y,x,z);

160       end;

161     cut:=0;

162     cuts:=n;

163     dfs1(1);

164     work;

165     writeln(ans);

166 end;

167 

168 begin

169     while true do

170       init;

171 end.
View Code

 

你可能感兴趣的:(tree)