甲级1004 Counting Leaves
A family hierarchy is usually presented by a pedigree tree. Your job is to count those family members who have no child.
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, and M (<N), the number of non-leaf nodes. 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 01
.
The input ends with N being 0. That case must NOT be processed.
Output Specification:
For each test case, you are supposed to count those family members who have no child for every seniority level starting from the root. The numbers must be printed in a line, separated by a space, and there must be no extra space at the end of each line.
The sample case represents a tree with only 2 nodes, where 01
is the root and 02
is its only child. Hence on the root 01
level, there is 0
leaf node; and on the next level, there is 1
leaf node. Then we should output 0 1
in a line.
Sample Input:
2 1
01 1 02
Sample Output:
0 1
题意:一个家族的层次关系可由血缘树表示。输入家族总人数N和非叶子节点的人数M(非叶子节点即有子女的人),之后M行输入非叶子节点的子节点。最后求出每一层级中,叶子节点的数量
分析:一开始想到的是构建一个树并层序遍历,然后输出每一层的叶子节点数量。这个做法写完后有两个点就超时了。
看了一眼其他人的想法,其中提到一句:每个节点的子节点对其影响不大,重要的是其父节点。对于这道题确实是这样,父节点可以推导出当前层级。而子节点则无法提供任何有用信息。
所以每个节点只存储父节点,层级,是否有子节点的信息。
整个程序先读入所有信息,将所有节点的父节点确定下来,然后再求每个节点的层级,这个过程用递归实现,实际上由于我没有用vector来存储各个节点的信息,而是用一个已经开好的数组然后用ID做下标访问信息,所以这里求各个节点层级的速度我认为应该相当快。
最后一步就是遍历所有节点的信息,得到结果。
坑点:1 0的测试样例输出必须为1。
AC代码如下:
1 #include <iostream> 2 using namespace std; 3 4 struct Node 5 { 6 int parent; 7 int level; //parent的层级+1 8 bool haveChildren; 9 bool isFamily; 10 }; 11 12 Node family[100]; 13 int levelLeaf[105]; 14 int maxLevel = 0; 15 16 int getlevel(int ID) 17 { 18 if (ID == 1) return 0; 19 if (family[ID].level == 0) 20 { 21 family[ID].level = getlevel(family[ID].parent) + 1; 22 if (family[ID].level > maxLevel) maxLevel = family[ID].level; 23 } 24 return family[ID].level; 25 } 26 27 int main() 28 { 29 int N, M; 30 scanf("%d", &N); 31 if (N == 0) return 0; 32 scanf("%d", &M); 33 int ID_in; 34 family[1].isFamily = true; 35 for (int i = 0; i < M; i++) 36 { 37 scanf("%d", &ID_in); 38 family[ID_in].haveChildren = true; 39 family[ID_in].isFamily = true; 40 int child_count,child_ID; 41 scanf("%d", &child_count); 42 for (int j = 0; j < child_count; j++) 43 { 44 scanf("%d", &child_ID); 45 family[child_ID].parent = ID_in; 46 family[child_ID].isFamily = true; 47 } 48 } 49 for (int i = 0; i < 100; i++) 50 { 51 if (family[i].isFamily == true && family[i].haveChildren == false) 52 { 53 levelLeaf[getlevel(i)]++; 54 } 55 } 56 bool flag = false; 57 for (int i = 0; i <= maxLevel; i++) 58 { 59 if (flag == false) flag = true; 60 else printf(" "); 61 printf("%d", levelLeaf[i]); 62 } 63 return 0; 64 }
然后是两个点有超时,其它点通过的代码(如果有大神发现问题,请不吝赐教):
1 #include <iostream> 2 #include <vector> 3 #include <unordered_map> 4 #include <string> 5 #include <queue> 6 using namespace std; 7 8 struct Node 9 { 10 string ID; 11 vector<string> children; 12 int level; 13 }; 14 15 unordered_map<string, Node*> mapp; 16 queue<string> analyse_que; 17 18 int main() 19 { 20 /*N为所有结点数,M为非叶子节点数,求每一层的叶子节点数*/ 21 int N, M; 22 cin >> N >> M; 23 string ID_in; 24 int children_count; 25 Node root; 26 root.ID = "01"; 27 root.level = 0; 28 mapp["01"] = &root; 29 for (int i = 0; i < M; i++) 30 { 31 cin >> ID_in; 32 auto it = mapp.find(ID_in); 33 if (it == mapp.end()) 34 { 35 Node node; 36 mapp[ID_in] = &node; 37 node.ID = ID_in; 38 } 39 it = mapp.find(ID_in); 40 cin >> children_count; 41 string child_ID; 42 for (int j = 0; j < children_count; j++) 43 { 44 cin >> child_ID; 45 (it->second)->children.push_back(child_ID); 46 auto child_it = mapp.find(child_ID); 47 if (child_it == mapp.end()) 48 { 49 //Node node;此处不能声明一个局部变量 50 Node* node_p = new Node; 51 mapp[child_ID] = node_p; 52 node_p->ID = child_ID; 53 } 54 } 55 } 56 int non_leaf_count = 0; 57 analyse_que.push("01"); 58 int leaf = 0; 59 int now_level = 0; 60 while (!analyse_que.empty()) 61 { 62 string id = analyse_que.front(); 63 analyse_que.pop(); 64 Node* p = mapp[id]; 65 if ((p->children).empty()) 66 { 67 if (p->level != now_level) 68 { 69 printf("%d ", leaf); 70 for (int i = 0; i < (p->level - now_level - 1); i++) 71 printf("0 "); 72 leaf = 1; 73 now_level=p->level; 74 } 75 else 76 { 77 leaf++; 78 } 79 } 80 else 81 { 82 for (auto it = (p->children).begin(); it != (p->children).end(); it++) 83 { 84 Node* child_p = mapp[*it]; 85 child_p->level = p->level + 1; 86 analyse_que.push(child_p->ID); 87 } 88 } 89 } 90 printf("%d", leaf); 91 return 0; 92 }