(六)堆排序
实现代码:
/*!
* \brief from wiki
* \param d
* \param ind
* \param len
*/
void sift(int d[], int ind, int len)
{
//#置i为要筛选的节点#%
int i = ind;
//#c中保存i节点的左孩子#%
int c = i * 2 + 1; //#+1的目的就是为了解决节点从0开始而他的左孩子一直为0的问题#%
while(c < len)//#未筛选到叶子节点#%
{
//#如果要筛选的节点既有左孩子又有右孩子并且左孩子值小于右孩子#%
//#从二者中选出较大的并记录#%
if(c + 1 < len && d[c] < d[c + 1])
c++;
//#如果要筛选的节点中的值大于左右孩子的较大者则退出#%
if(d[i] > d[c]) break;
else
{
//#交换#%
int t = d[c];
d[c] = d[i];
d[i] = t;
//#重置要筛选的节点和要筛选的左孩子#%
i = c;
c = 2 * i + 1;
}
}
return;
}
void heap_sort(int d[], int n)
{
//#初始化建堆, i从最后一个非叶子节点开始#%
for(int i = (n - 2) / 2; i >= 0; i--)
sift(d, i, n);
for(int j = 0; j < n; j++)
{
//#交换#%
int t = d[0];
d[0] = d[n - j - 1];
d[n - j - 1] = t;
//#筛选编号为0 #%
sift(d, 0, n - j - 1);
}
}
/*!
* 堆排序
*/
double HeapSort(int *data, int size)
{
double res = 0;
//EClock<> Ek;
heap_sort(data, size);
//res = Ek.microsecond();
return res;
}
测试结果:
单位:us
10 | 0.30187 |
20 | 0.60374 |
50 | 1.50935 |
100 | 3.622439 |
200 | 7.546748 |
500 | 22.03651 |
1000 | 48.90293 |
2000 | 167.5378 |
3000 | 213.7239 |
4000 | 230.9305 |
5000 | 296.1344 |
6000 | 370.3944 |
7000 | 431.3721 |
8000 | 519.82 |
9000 | 570.5342 |
10000 | 646.0017 |
20000 | 1390.413 |
50000 | 4723.057 |
100000 | 8285.424 |
200000 | 19074.86 |
500000 | 63523.7 |
800000 | 90019.43 |
1000000 | 122265.2 |