Given a non-empty tree with root R, and with weight Wi assigned to each tree node Ti. The weight of a path from R to L is defined to be the sum of the weights of all the nodes along the path from R to any leaf node L.
Now given any weighted tree, you are supposed to find all the paths with their weights equal to a given number. For example, let's consider the tree showed in Figure 1: for each node, the upper number is the node ID which is a two-digit number, and the lower number is the weight of that node. Suppose that the given number is 24, then there exists 4 different paths which have the same given weight: {10 5 2 7}, {10 4 10}, {10 3 3 6 2} and {10 3 3 6 2}, which correspond to the red edges in Figure 1.
Figure 1
Input Specification:
Each input file contains one test case. Each case starts with a line containing 0 < N <= 100, the number of nodes in a tree, M (< N), the number of non-leaf nodes, and 0 < S < 230, the given weight number. The next line contains N positive numbers where Wi (<1000) corresponds to the tree node Ti. Then M lines follow, each in the format:
ID K ID[1] ID[2] ... ID[K]
where ID is a two-digit number representing a given non-leaf node, K is the number of its children, followed by a sequence of two-digit ID's of its children. For the sake of simplicity, let us fix the root ID to be 00.
Output Specification:
For each test case, print all the paths with weight S in non-increasing order. Each path occupies a line with printed weights from the root to the leaf in order. All the numbers must be separated by a space with no extra space at the end of the line.
Note: sequence {A1, A2, ..., An} is said to be greater than sequence {B1, B2, ..., Bm} if there exists 1 <= k < min{n, m} such that Ai = Bifor i=1, ... k, and Ak+1 > Bk+1.
Sample Input:20 9 24 10 2 4 3 5 10 2 18 9 7 2 2 1 3 12 1 8 6 2 2 00 4 01 02 03 04 02 1 05 04 2 06 07 03 3 11 12 13 06 1 09 07 2 08 10 16 1 15 13 3 14 16 17 17 2 18 19Sample Output:
10 5 2 7 10 4 10 10 3 3 6 210 3 3 6 2
分析: 找出从根到叶子节点,花销为给定值的路径,并按照一定次序排列。
正确代码如下:
#include <iostream> #include <vector> #include <set> #include <algorithm> using namespace std; struct node{ int id; int wei; int pre; }; vector<node> tree; vector<vector<node> > path; int wei; void calWei(vector<node>& v){ int i; for(i=0; i<v.size(); i++){ vector<node> possiblePath; node tmp; tmp = v[i]; int w = 0; while(tmp.id!= 0){ w += tmp.wei; possiblePath.push_back(tmp); tmp = tree[tmp.pre]; } w += tree[0].wei; if(w == wei){ possiblePath.push_back(tree[0]); path.push_back(possiblePath); } } } bool cmp(vector<node> a, vector<node> b){ int i = a.size()-1; int j = b.size()-1; for(; i>=0&&j>=0; i--,j--){ if(a[i].wei != b[j].wei){ return a[i].wei>b[j].wei; } } if(i==0 && j!=0){ return true; }else if(i!=0 && j==0){ return false; } return false; } int main(int argc, char** argv) { int n, m, i; scanf("%d%d%d",&n,&m,&wei); tree.resize(n); for(i=0; i<n; i++){ tree[i].id= i; scanf("%d",&tree[i].wei); } set<int> nonLeaf; for(i=0; i<m; i++){ int index, num, t, j; scanf("%d%d",&index,&num); nonLeaf.insert(index); for(j=0; j<num; j++){ scanf("%d",&t); tree[t].pre = index; } } vector<node> leafNode; for(i=0; i<n; i++){ if(nonLeaf.count(i)==0){ leafNode.push_back(tree[i]); } } calWei(leafNode); sort(path.begin(), path.end(), cmp); for(i=0; i<path.size(); i++){ for(int j=path[i].size()-1; j>=0; j--){ if(j==0){ printf("%d\n",path[i][j].wei); }else{ printf("%d ",path[i][j].wei); } } } return 0; }
解法二:
#include <iostream> #include <vector> #include <algorithm> using namespace std; vector<int> wei; struct node{ int pre, wei; }; vector<node> tree; int countWei(int leaf, vector<int> &vec){ int addr=leaf, total=0; while(true){ vec.push_back(wei[addr]); total += wei[addr]; if(addr == 0) break; addr = tree[addr].pre; } return total; } int main(int argc, char** argv) { int N, M, S; scanf("%d%d%d",&N,&M,&S); int i; wei.resize(N); for(i=0; i<N; i++){ scanf("%d",&wei[i]); } int fa, num, t; tree.resize(N); vector<int> isLeaf(N,1); for(i=0; i<M; i++){ scanf("%d%d",&fa,&num); isLeaf[fa] = 0; for(int j=0; j<num; j++){ scanf("%d",&t); tree[t].pre = fa; } } vector<vector<int> >result; for(i=0; i<N; i++){ if(isLeaf[i]==1){ vector<int> tmp; int wei = countWei(i, tmp); if(wei == S){ reverse(tmp.begin(), tmp.end()); result.push_back(tmp); } } } sort(result.begin(), result.end()); for(i=result.size()-1; i>=0; i--){ for(int j=0; j<result[i].size(); j++){ if(j==0) printf("%d",result[i][j]); else printf(" %d",result[i][j]); } printf("\n"); } return 0; }