A tree is a connected graph that doesn't contain any cycles.
The distance between two vertices of a tree is the length (in edges) of the shortest path between these vertices.
You are given a tree with n vertices and a positive number k. Find the number of distinct pairs of the vertices which have a distance of exactly k between them. Note that pairs (v, u) and (u, v) are considered to be the same pair.
The first line contains two integers n and k (1 ≤ n ≤ 50000, 1 ≤ k ≤ 500) — the number of vertices and the required distance between the vertices.
Next n - 1 lines describe the edges as "ai bi" (without the quotes) (1 ≤ ai, bi ≤ n, ai ≠ bi), where ai andbi are the vertices connected by the i-th edge. All given edges are different.
Print a single integer — the number of distinct pairs of the tree's vertices which have a distance of exactly k between them.
Please do not use the %lld specifier to read or write 64-bit integers in С++. It is preferred to use thecin, cout streams or the %I64d specifier.
5 2 1 2 2 3 3 4 2 5
4
题目链接:here
对于一棵根节点为r的树,经过节点r且长度为k的路径可分为两种情况:
a、节点r为这条路径的端点;
b、节点r为这条路径中途的点;
我们不妨用一个变量dp[r][k]记录通过r且长度为k的路径数目,
则dp[r][k]为a、b两种情况下的和。
- #include<cstdio>
- #include<cstring>
- #include<vector>
- #define N 50005
- using namespace std;
- vector<int> vec[N];
- int dp[N][510],ans;
- void dfs(int root,int f,int x)
- {
- for(int i=0;i<=x;i++) dp[root][i]=0;
- dp[root][0]=1;
- for(int i=0;i<vec[root].size();i++) {
- int son=vec[root][i];
- if(son!=f) {<span style="font-family: Arial, Helvetica, sans-serif;">//由于是用无向图方式来储存树的,所以加此判断以保持dfs的方向</span>
- dfs(son,root,x);
- for(int j=0;j<x;j++) ans+=dp[son][j]*dp[root][x-j-1];
- for(int j=1;j<=x;j++) dp[root][j]+=dp[son][j-1];
- }
- }
- }
- int main()
- {
- int n,k,a,b;
- while(scanf("%d%d",&n,&k)!=EOF) {
- for(int i=0;i<n-1;i++) {
- scanf("%d%d",&a,&b);
- vec[a].push_back(b);
- vec[b].push_back(a);
- }
- ans=0;
- dfs(1,0,k);
- printf("%d\n",ans);
- }
- return 0;
- }