実用的なアプリケーションのスタックとヒープ

実用的なアプリケーションのスタックとヒープ

1スタックの概念
スタックメモリは、ストレージ修飾の配列とみなすことができるが、しかし、二分木構造と格納タイプによってヒープメモリを有するスタックが小さい山とのスタックに分割することができます。小さなパイル(杭)において、最小値がルートノードからの経路の各ノードに、スタック・ノード・キー(最大)の上部に位置するキーのその左右の子供に等しい(より大きい)未満の任意のノード鍵配列要素にシーケンスがインクリメントされると(デクリメント)。
構造は、ヒープのサイズを表します

2.ヒープ作成し
、それから、形質転換単にアレイと見なすことができるヒープ。したがって、スタックはまた、いくつかの変換を作成することができる
第一の工程、方法インデックスのソート構築することにより層で完全バイナリツリー内の要素の配列
第二工程・を、下方調整方法によって、この二分木は最小調整しますヒープの
原則:非リーフノードがルートノードまでとなっているの最後の調整から始め、各ノードは小さなヒープにそのサブ木の性質を満たすように調整されます。
具体的な調整方法:
1.ノードの親のインデックスと仮定
2.親の左の子ノードを* = 2 +左1。
3であれば右の子右=親* 2 + 1は、左右のうちの最小値を見つける存在します子供
4.子について、親の比較調整の小さい方の端場合はあまり、その小さい未満である
か、小さな子供交換を持つ要素の親調整は自然の小さな山の後に成立しない場合、それがなるまで調整していきますサブツリー満たす性質ができます。
3.ヒープの挿入および欠失
によるヒープの特殊な性質のために、それほど多くの問題への平均的なバイナリツリーよりも挿入および欠失
1。ヒープインサート:スタック内の新しい要素が完成後ろに最小化されている挿入し、挿入後、挿入した後、プロパティはツリーノードのヒープを満たしていない場合は、調整する必要があります。
方法は
、彼らが小さな山を持っているので、そのため、葉のみからサブツリーのルートノードに調整する必要があります。ノードは父親よりも小さい場合はまず、自然の小さな山を満たし、あなたがそうヒープ全体まで数回繰り返し、自然の小さな山を満たすために調整を行った後、上方に調整する必要があり、そのノードの父を見つけます
2.ヒープ削除:軽く削除されていないヒープを削除し、完全に小さなパイル構造を破壊した単語を削除しないためには、それはもはやあなたは、このプロパティを保持したい場合は、我々は再する必要があり、自然の小さなヒープを持っていませんヒープを構築し、その後、時間が非常に複雑になります。
この方法は、
スタック要素のスタックトップの最後の要素を置き換えます
、スタックの要素数が押さ標準コントロールなので、それが唯一のスタックインデックスを削除する最後の要素保存する必要があるため
、スタック構造が破壊された場合、このケースをしたがって、スタックが可能にソートすることも可能であり、それは単純な下方修正は、自然を再ためにスタックを満たすために小さくすることができ必要とし、その時間の複雑さはNを記録しています。
アプリケーション・ヒープ

1.プライオリティキューの
アイデア分析:キューイングプライオリティキューは、この現象を説明するために使用することができます本当です。あなたは食べ物を買うために並ぶようになるだろう、とあなたが早く行けば、あなたはすぐに遅れて行くだけでなく、購入することができた場合、それらは他の人の後ろに持っているでしょう、あなたは遅れて購入するだろう、この時間も必要です一部の人は特に遅い場合に、問題を検討し、それが優先と考えられます。優先度はより少ない数が、それは迅速にアクセスすることができ、より高い優先度に設定され、それはより迅速にデータを処理することができることによって特徴付けられる、私は以下のコードを入れています。

void PriorityQueueInit(PriorityQueue* q)
{
    assert(q);
    q->_size=0;
    memset(q->_a,0,sizeof(DataType)*N);
}

void PriorityQueuePush(PriorityQueue* q, DataType x) 
{
    assert(q);
    if(q->_size>=N)
    {
    printf("PriorityQueuefull\n");
    return;
    }

    q->_a[q->_size++]=x;
     AdjustUp(q->_a,q->_size,q->_size-1);


}
void PriorityQueuePop(PriorityQueue* q)
{
    assert(q);
    if(NULL==q)
    {
        printf("PriorityQueueEmpty\n");
        return;
    }
    q->_a[0]=q->_a[q->_size-1];
    q->_size--;
    AdjustDown(q->_a,q->_size,0);





}
DataType PriorityQueueTop(PriorityQueue* q)
{
    assert(q);
    if(NULL==q)
    {
        printf("PriorityQueueEmpty\n");
        return;
    }

   return q->_a[0];
}
size_t PriorityQueueSize(PriorityQueue* q)
{
   assert(q);
   return q->_size;

}
size_t PriorityQueueEmpty(PriorityQueue* q)
{
    assert(q);
    return q->_size;
}
void HeapSort(DataType* a, size_t n)
{
    int i=0;
    assert(a);
    MakeHeap(a,n);



    while(n>0)
    {
    printf("%d ",a[0]);
    a[0]=a[n-1];
    n--;
    AdjustDown(a,n,0);
    }

  
  
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76

最初のk個の(大量のデータTOPK問題)210百万円の最大数を探す
:アイデア分析、その後100億数が必要とされる一見、100億の数、確かに非常に大きな、4バイトの数の合計、通常のコンピュータである収納スペースの40Gは、実際には不可能です。しかし、この質問は確かに収納スペースが十分でないので、私たちは何の発言権を持たないヒープ100億のデータを作成させることができない、時間の複雑さが大きい、右・プラクティスです
。1. k個の要素を作成します。小さなパイル
2.サイクル、最後の要素と最初の要素を交換し、その後自然の小さな山を満たすために下方調整、この数は、ルートよりも小さい場合には、直接廃棄、または調整することができます反応器内のすべてのデータの最大数のいくつかは、あなたが探しているので、あなたがして印刷することができます日まで
、次のようにメインのコードは次のようになります。

#include"Heap.h"
void MakeHeap(DataType* a, size_t n)//构建堆
{
    int i=(n-1)>>1;
    for(;i>=0;i--)
    {
        AdjustDown(a,n,i);
    }
}
void AdjustDown(DataType* a, size_t n, int root)//向下调整
{
    int parent =root;
    int child=2*parent+1;
    while(child<n)
    {
        if((child+1)<n&&a[child+1]<a[child])//右孩子存在且右孩子大于左孩子
        {
            ++child;//指向右孩子
        }
        if(a[child]<a[parent])
        {
            DataType tmp;
            tmp=a[child];
            a[child]=a[parent];
            a[parent]=tmp;

            parent=child;
            child=2*parent+1;
        }
        else
        {
            break;
        }

    }


}
void AdjustUp(DataType* a, size_t n, int child)//向上调整
{
    int parent=(child-1)>>1;
    while(child>0)
    {
        if(a[child]<a[parent])
        {
            DataType tmp;
            tmp=a[child];
            a[child]=a[parent];
            a[parent]=tmp;

            child=parent;
            parent=(child-1)>>1;
        }
        else
        {
            break;
        }
    }

}
void TopK(DataType* a, size_t n, size_t k)
{
    int i;
    MakeHeap(a,k);//建小堆
    for(i=k;i<n;i++)
    {
        a[0]=a[i];
        AdjustDown(a,k,0);

    }
    for(i=0;i<k;i++)
    {
        printf("%d ",a[i]);
    }

  
  
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75

おすすめ

転載: blog.csdn.net/mad_sword/article/details/93399526