find a heapified array when converting it to a sorted array, the total number of exchanges is maximal possible

匿名 (未验证) 提交于 2019-12-03 02:27:02

问题:

Inspired by this post, I googled the worst case of heapsort and found this question on cs.stackexchange.com, but the only answer didn't really answer the question, so I decided to dig it out myself. After hours of reasoning and coding, I've solved it. and I think this question belongs better in SO, so I post it up here.
The problem is to find a heapified array containing different numbers from 1 to n, such that when converting it to a sorted array, the total number of exchanges in all sifting operations is maximal possible.

回答1:

Of course there is a brute force algorithm which calculates all possible of the heapified arrays and counts the number of exchanges for each one, and I have done that to verify the result of the solution below.


  • let's start from N=1: 1

  • N=2: apparently, it's [2, 1]

  • N=3: [3, x, 1].

  • N=4: [4, x, y, 1]
    After first extract-max, we need heapify [1, x, y]. If we sift it to the case when N=3, [3, 2, 1], since this sifting operation incurs the most swaps which is equal to the "height", plus the maximal number of exchanges when N=3, so that's the scenario of maximal number of exchanges when N=4. Thus, we do the "siftDown" version of heapify backwards to [3, 2, 1]: swap 1 with its parent until 1 is the root. So x=2, y=3

  • N = n: [n,a,b,c,...,x,1]
    So, by induction, we do the same thing when N=n: after first extract-max, we sift down [1, a, b, c, ..., x] to the heapified array when N= n-1. So we do this backwards, get what we what.

Here is the code that outputs the heapified array which meets the requirements when you input N:

#include<stdio.h>  const int MAXN = 50001;  int  heap[MAXN];  int main() {     int n;     int len,i,j;     while(scanf("%d",&n)!=EOF)     {         heap[1]=1;         len=1;         for(i=2;i<=n;i++)         {             j=len;             while(j>1)             {                 heap[j]=heap[j/2];                 j/=2;             }             heap[1]=i;             heap[++len]=1;         }         for(i=1;i<=n;i++)         {             if(i!=1) printf(" ");             printf("%d",heap[i]);         }         printf("\n");     }     return 0; } 


标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!