1147 Heaps
In computer science, a heap is a specialized tree-based data structure that satisfies the heap property: if P is a parent node of C, then the key (the value) of P is either greater than or equal to (in a max heap) or less than or equal to (in a min heap) the key of C. A common implementation of a heap is the binary heap, in which the tree is a complete binary tree. (Quoted from Wikipedia at https://en.wikipedia.org/wiki/Heap_(data_structure))
Your job is to tell if a given complete binary tree is a heap.
Input Specification:
Each input file contains one test case. For each case, the first line gives two positive integers: M (≤ 100), the number of trees to be tested; and N (1 < N ≤ 1,000), the number of keys in each tree, respectively. Then M lines follow, each contains N distinct integer keys (all in the range of int), which gives the level order traversal sequence of a complete binary tree.
Output Specification:
For each given tree, print in a line Max Heap if it is a max heap, or Min Heap for a min heap, or Not Heap if it is not a heap at all. Then in the next line print the tree’s postorder traversal sequence. All the numbers are separated by a space, and there must no extra space at the beginning or the end of the line.
Sample Input:
3 8 98 72 86 60 65 12 23 50 8 38 25 58 52 82 70 60 10 28 15 12 34 9 8 56
Sample Output:
Max Heap 50 60 65 72 12 23 86 98 Min Heap 60 58 52 38 82 70 25 8 Not Heap 56 12 34 28 9 8 15 10
题意
给定 M 个完全二叉树的层序遍历结果,每个结果包含 N 个结点,需要我们判断这 M 个树是否为堆,并输出其后序遍历的结果。
思路
本题可以利用完全二叉树的性质,完全二叉树的层序遍历结果在数组中有如下性质(下标从 1 开始):
下标为 u 的根结点的左孩子下标为 u*2
下标为 u 的根结点的右孩子下标为 u*2+1
具体思路如下:
先输入层序遍历的数组,注意是从下标 1 开始输入,方便后续使用其性质。
判断是否为堆,用 lt 和 gt 变量来标记,如果出现根结点要小于其孩子结点,则标记 lt 为 true ;反之,标记 gt 为 true 。
根据 lt 和 gt 标记结果输出对应答案,如果 lt 和 gt 都为 true ,说明该二叉树并不是堆;如果 lt 为 true ,说明该二叉树是小根堆;如果 gt 为 true ,说明该二叉树是大根堆。
输出该二叉树的后序遍历结果,同样可以利用上述提到的下标性质进行递归遍历。
代码
#include<bits/stdc++.h> using namespace std; const int N = 1010; int h[N]; int m, n; //输出后序遍历结果遍历 void dfs(int u) { if (u > n) return; dfs(u * 2); dfs(u * 2 + 1); cout << h[u]; if (u != 1) cout << " "; } int main() { cin >> m >> n; while (m--) { //输入层序遍历数组 for (int i = 1; i <= n; i++) cin >> h[i]; //判断是否为堆 bool lt = false, gt = false; for (int i = 1; i <= n; i++) for (int j = 0; j < 2; j++) if (i * 2 + j <= n) { int a = h[i], b = h[i * 2 + j]; if (a < b) lt = true; else gt = true; } //根据判断结果输出对应类型 if (lt && gt) puts("Not Heap"); else if (lt) puts("Min Heap"); else puts("Max Heap"); //输出后序遍历结果 dfs(1); puts(""); } return 0; }