1053 Path of Equal Weight

Given a non-empty tree with root R, and with weight W​i​​ assigned to each tree node T​i​​. 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 the following figure: 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 the figure.

Input Specification:

Each input file contains one test case. Each case starts with a line containing 0, the number of nodes in a tree, M (<), the number of non-leaf nodes, and 0, the given weight number. The next line contains N positive numbers where W​i​​ (<) corresponds to the tree node T​i​​. 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 { is said to be greater than sequence { if there exists 1 such that A​i​​=B​i​​ for ,, and A​k+1​​>B​k+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 19
 

Sample Output:

10 5 2 7
10 4 10
10 3 3 6 2
10 3 3 6 2

 

题意:

  给出一棵树,每个节点既有编号又有权值,找出所有从根节点到叶子结点权值之和等于s的所有路径。

思路:

  构造一个结构体,结构体中既有权重又有孩子结点,同时还有当前结点到达根节点的权重之和。其实寻找路径比较好找,我们用简单的DFS就能够把路径找到,但是问题要求输出的路径按照降序输出,看了别人的代码后,发现,在遍历孩子结点的时候如果我们能够保证孩子结点是由大到小的顺序,那么路径也就一定是由大到小的顺序。明白了只一点,这道题就简单了。

Code:

 1 #include <bits/stdc++.h>
 2 
 3 using namespace std;
 4 
 5 struct Node {
 6     int val;
 7     vector<int> sons;
 8     int father = -1;
 9     int sum = 0;
10 };
11 
12 vector<int> leaf;
13 vector<Node> v;
14 
15 bool cmp(int a, int b) { return v[a].val > v[b].val; }
16 
17 void DFS(int index, int s) {
18     if (v[index].father != -1) {
19         int father = v[index].father;
20         v[index].sum = v[father].sum + v[index].val;
21     }
22     if (v[index].sons.size() == 0) {
23         if (v[index].sum == s) {
24             vector<int> path;
25             while (v[index].father != -1) {
26                 path.push_back(v[index].val);
27                 index = v[index].father;
28             }
29             path.push_back(v[index].val);
30             reverse(path.begin(), path.end());
31             for (int i = 0; i < path.size(); ++i) {
32                 if (i == 0)
33                     cout << path[i];
34                 else
35                     cout << " " << path[i];
36             }
37             cout << endl;
38         }
39         return;
40     }
41     for (int son : v[index].sons) DFS(son, s);
42 }
43 
44 int main() {
45     int n, m;
46     long long s;
47     cin >> n >> m >> s;
48     v.resize(n);
49     for (int i = 0; i < n; ++i) {
50         cin >> v[i].val;
51         v[i].sum = v[i].val;
52     }
53     for (int i = 0; i < m; ++i) {
54         int index, k, son;
55         cin >> index >> k;
56         v[index].sum = v[index].val;
57         for (int j = 0; j < k; ++j) {
58             cin >> son;
59             v[index].sons.push_back(son);
60             v[son].father = index;
61         }
62         sort(v[index].sons.begin(), v[index].sons.end(), cmp);
63     }
64     DFS(0, s);
65     return 0;
66 }

 

posted @ 2020-05-07 22:06  Veritas_des_Liberty  阅读(188)  评论(0编辑  收藏  举报