堆排序 | ||
---|---|---|
Time Limit: 1000 MS | Memory Limit: 1000 KB |
Description
给定一维int型数组, 请构造一棵最小堆. 总是优先向左子树调整.
Input
输入第1行有一个int型正整数m (m<100), 表示有m行输入.
每行输入的第一个数为int型正整数n (8<n<1000), 后面接着输入n个int型整数.
Output
输出m行, 每行为排好序的输出.
Sample Input
2
7 3 8 4 1 6 3 2
8 2 4 5 9 8 7 6 3
Sample Output
1 3 2 8 6 3 4
2 3 5 4 8 7 6 9
从最后一个元素的父节点开始,依次向前查找节点。比较节点与孩子的大小,将最小者放在根节点,且进行递归,将交换后的子节点作为新的根进行最小堆的构建。此外,2i+2表示节点i的右子树;2i+1表示节点i的左子树。可通过2i+1、2i+2与n进行大小比较来判断节点i的左右子树是否存在
#include<iostream>
using namespace std;
int main()
{
int T = 0;
cin >> T;
for (int t = 0; t < T; t++)
{
int n = 0;
cin >> n;
int MinHeap[2001];
int pos = 0;
for (int i = 0; i < n; i++)
{
int m = 0;
cin >> m;
MinHeap[i] = m;
}
for (int i = n; i < 2001; i++)
{
MinHeap[i] = 1000;
}
for (int i = n-1; i >= 0; i--)
{
int pos = i;
MinHeap[i];
if ((pos * 2 + 2) < n) //右子树存在
{
while ( MinHeap[pos * 2 + 1] <MinHeap[pos]|| MinHeap[pos * 2 + 2] < MinHeap[pos])
{
if (MinHeap[pos * 2 + 1] <= MinHeap[pos * 2 + 2])
{
int temp = MinHeap[pos];
MinHeap[pos] = MinHeap[pos * 2 + 1];
MinHeap[pos * 2 + 1] = temp;
pos = pos * 2 + 1;
}
else
{
int temp = MinHeap[pos];
MinHeap[pos] = MinHeap[pos * 2 + 2];
MinHeap[pos * 2 + 2] = temp;
pos = pos * 2 + 2;
}
}
}
else if ((pos * 2 + 1) < n)//左子树存在
{
if (MinHeap[pos * 2 + 1] < MinHeap[pos])
{
int temp = MinHeap[pos];
MinHeap[pos] = MinHeap[pos * 2 + 1];
MinHeap[pos * 2 + 1] = temp;
}
}
}
for (int i = 0; i < n; i++) //进行输出
{
if (i != n - 1)cout << MinHeap[i] << " ";
else cout << MinHeap[i] << endl;
}
}
return 0;
}