注意点:
- 枚举阶段时需要用dfs预处理每个点的深度.
#include<cstdio>
#include<iostream>
#include<cstring>
#include<algorithm>
using namespace std;
const int MAXN=2e4,MAXM=3e4;
struct Edge{
int from,to,w,nxt;
}e[MAXM];
int head[MAXN],edgeCnt=1;
void addEdge(int u,int v,int w){
e[++edgeCnt].from=u;
e[edgeCnt].to=v;
e[edgeCnt].w=w;
e[edgeCnt].nxt=head[u];
head[u]=edgeCnt;
}
bool vis[MAXN],w[MAXN];
int siz[MAXN];
int pos,ans;
void dfs_find(int restSiz,int x){
vis[x]=1;
siz[x]=1;
int maxSiz=0;
for(int i=head[x];i;i=e[i].nxt){
int nowV=e[i].to;
if(vis[nowV]||w[nowV])continue;
dfs_find(restSiz,nowV);
siz[x]+=siz[nowV];
maxSiz=max(maxSiz,siz[nowV]);
}
maxSiz=max(maxSiz,restSiz-siz[x]);
if(maxSiz<ans)ans=maxSiz,pos=x;
}
int dep[MAXN],tot,cnt[MAXN];
int a[MAXN],b[MAXN];
void dfs(int x){
vis[x]=1;
for(int i=head[x];i;i=e[i].nxt){
int nowV=e[i].to,nowW=e[i].w;
if(vis[nowV]||w[nowV])continue;
a[++tot]=nowV,b[nowV]=b[x];
cnt[b[x]]++;
dep[nowV]=dep[x]+nowW;//
dfs(nowV);
}
}
bool cmp(int x,int y){
return dep[x]<dep[y];
}
int Ans;
void reset(){
memset(dep,0,sizeof(dep));
memset(cnt,0,sizeof(cnt));
memset(vis,0,sizeof(vis));
tot=1;
}
int k;
void work(int restSiz,int x){
memset(vis,0,sizeof(vis));
ans=restSiz;
dfs_find(restSiz,x);
reset();
a[tot]=b[pos]=pos;
w[pos]=1,cnt[pos]++;
for(int i=head[pos];i;i=e[i].nxt){
int nowV=e[i].to,nowW=e[i].w;
if(vis[nowV]||w[nowV])continue;
a[++tot]=b[nowV]=nowV;
cnt[nowV]++,dep[nowV]=nowW;
dfs(nowV);
}
sort(a+1,a+1+tot,cmp);
int l=1,r=tot;
cnt[b[a[1]]]--;
while(l<r){
while(dep[a[l]]+dep[a[r]]>k)cnt[b[a[r--]]]--;
Ans+=r-l-cnt[b[a[l]]];
cnt[b[a[++l]]]--;
}
int nowU=pos;
for(int i=head[nowU];i;i=e[i].nxt){
int nowV=e[i].to;
if(w[nowV])continue;
work(siz[nowV],nowV);
}
}
void init(){
memset(head,0,sizeof(head));
edgeCnt=1;
}
int main(){
int n;
while(1){
scanf("%d%d",&n,&k);
if(!n)break;
init();
for(int i=1;i<=n-1;i++){
int u,v,cost;
scanf("%d%d%d",&u,&v,&cost);
addEdge(u,v,cost);
addEdge(v,u,cost);
}
memset(w,0,sizeof(w));
Ans=0;
work(n,1);
printf("%d\n",Ans);
}
return 0;
}