欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

C語言排序之?堆排序

 更新時(shí)間:2022年04月19日 10:44:16   作者:sndapk  
這篇文章主要介紹了C語言排序之堆排序,文章基于C語言的相關(guān)資料展開詳細(xì)內(nèi)容,具有一定的參考資料,需要的小伙伴可以參考一下

前言:

堆是具有以下性質(zhì)的完全二叉樹

每個(gè)節(jié)點(diǎn)大于或等于其左右子節(jié)點(diǎn),此時(shí)稱為大頂(根)堆

?每個(gè)節(jié)點(diǎn)小于或等于其左右子節(jié)點(diǎn),此時(shí)稱為小頂(根)堆

完全二叉樹在數(shù)組中下標(biāo)換算公式

假設(shè)堆根節(jié)點(diǎn)從1開始編號(hào)(從1開始方便計(jì)算,0下標(biāo)空著)
下面以編號(hào)為i的非根節(jié)點(diǎn)為例,計(jì)算其關(guān)聯(lián)節(jié)點(diǎn)的下標(biāo)公式為:
其父節(jié)點(diǎn):i/2
其左孩子:2i
其右孩子:2i+1

注:把這個(gè)完全二叉樹按層序遍歷放入數(shù)組(0下標(biāo)不用),則滿足上面的關(guān)系表達(dá)

代碼工作流程

整體流程

a. 根據(jù)節(jié)點(diǎn)換算公式先從最下層非葉節(jié)點(diǎn)開始,依次從右到左(自下而上)一直到根創(chuàng)建初始堆

b. 循環(huán)n-1次,依次執(zhí)行:條件判斷后交換堆頂和堆尾元素
重建除堆尾外元素為新堆,一直到根

重建堆函數(shù)流程

接收參數(shù)開始下標(biāo)和數(shù)組有效長度
保存堆頂,自上而下建堆,如果堆頂(臨時(shí)堆頂)比子節(jié)點(diǎn)?。ù箜敹阎校?,則孩子賦值給臨時(shí)堆頂位置(不需要swap函數(shù)交換,swap沒必要),并讓臨時(shí)堆頂位置指定子節(jié)點(diǎn)
for循環(huán)終止一定會(huì)找到合適的位置,此時(shí)臨時(shí)堆頂指向的位置可能是函數(shù)調(diào)用時(shí)的位置,也可能發(fā)生改變(代碼中執(zhí)行了一次強(qiáng)制賦值)

大小頂堆使用場景

大頂堆用來做升序排序,小頂堆用來做降序排序

時(shí)間復(fù)雜度

O(nlogn)
不穩(wěn)定

代碼

#include <stdio.h>
#include <stdbool.h>

#define MAXSIZE 9

typedef struct {
    int r[MAXSIZE+1]; // first index used as tmp, not real data
    int len;
}SqList;

void swap(SqList *L, int i, int j) {
    int tmp = L->r[i];
    L->r[i] = L->r[j];
    L->r[j] = tmp;
}


void heap_adjust(SqList *L, int s, int len) {
    int temp, i;

    temp = L->r[s]; // s(start) index may be a invalid element in this heap and try adjust

    for (i=s*2; i<=len; i*=2) { // compare with child
        if (i<len && L->r[i] < L->r[i+1]) {
            i++; // select the max child
        }

        if (temp >= L->r[i]) {
            break; // need not adjust
        }

        L->r[s] = L->r[i]; //need not swap, because always use temp compare with next level child

        s = i; // next loop, now s sub tree root node may be a invalid element
    }

    L->r[s] = temp; // finally, must be found the right place(or not changed)

}


void heap_adjust_2(SqList *L, int s, int len) {
    printf("use test function\n");
    int temp, i;

    temp = L->r[s]; // s(start) index may be a invalid element in this heap and try adjust

    for (i=s*2; i<=len; i*=2) { // compare with child
        if (i<len && L->r[i] < L->r[i+1]) {
            i++; // select the max child
        }

        if (temp >= L->r[i]) {
            break; // need not adjust
        }

        swap(L, s, i); //need not swap, because always use temp compare with next level child

        s = i; // next loop, now s sub tree root node may be a invalid element
    }

    L->r[s] = temp; // finally, must be found the right place(or not changed)

}

void heap_sort(SqList *L) {
    // init serial to a heap first(type: big top), down->up and right->left
    int i, j;
    for (i=L->len/2; i>0; --i) {
        heap_adjust(L, i, L->len);
        //heap_adjust_2(L, i, L->len);
    }


    for (j=L->len; j>1; --j) {
        swap(L, 1, j);
        heap_adjust(L, 1, j-1);
    }

}

int main(void) {
    SqList list = {
        {999,50,10,90,30,70,40,80,60,20},
        MAXSIZE
    };

    heap_sort(&list);
    printf("after heap_sort:\n");
    for (int i=0; i<=MAXSIZE; i++) {
        printf("index: %d, value: %d\n",i,list.r[i]);
    }
    return 0;
}

output

?  c gcc sort_heap.c && ./a.out
after heap_sort:
index: 0, value: 999
index: 1, value: 10
index: 2, value: 20
index: 3, value: 30
index: 4, value: 40
index: 5, value: 50
index: 6, value: 60
index: 7, value: 70
index: 8, value: 80
index: 9, value: 90

到此這篇關(guān)于C語言排序之 堆排序的文章就介紹到這了,更多相關(guān)C語言排序內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • C++代碼實(shí)現(xiàn)五子棋小游戲

    C++代碼實(shí)現(xiàn)五子棋小游戲

    這篇文章主要為大家詳細(xì)介紹了C++代碼實(shí)現(xiàn)五子棋小游戲,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2022-05-05
  • wxWidgets自定義按鈕的方法

    wxWidgets自定義按鈕的方法

    這篇文章主要為大家詳細(xì)介紹了wxWidgets自定義按鈕的方法,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2019-02-02
  • C語言中計(jì)算二叉樹的寬度的兩種方式

    C語言中計(jì)算二叉樹的寬度的兩種方式

    這篇文章主要介紹了C語言中計(jì)算二叉樹的寬度的兩種方式的相關(guān)資料,需要的朋友可以參考下
    2017-04-04
  • C++報(bào)錯(cuò)`Null Pointer Dereference`的解決方法

    C++報(bào)錯(cuò)`Null Pointer Dereference`的解決方法

    在軟件開發(fā)中,Null Pointer Dereference 是一種常見的錯(cuò)誤,它發(fā)生在程序試圖訪問或操作一個(gè)空指針指向的內(nèi)存位置時(shí),這種情況通常會(huì)導(dǎo)致程序崩潰,給 debug 工作帶來很大困擾,今天,我們將探討如何解決 Null Pointer Dereference 報(bào)錯(cuò),需要的朋友可以參考下
    2024-07-07
  • C語言實(shí)現(xiàn)矩陣翻轉(zhuǎn)(上下翻轉(zhuǎn)、左右翻轉(zhuǎn))

    C語言實(shí)現(xiàn)矩陣翻轉(zhuǎn)(上下翻轉(zhuǎn)、左右翻轉(zhuǎn))

    這篇文章主要介紹了C語言實(shí)現(xiàn)矩陣翻轉(zhuǎn)(上下翻轉(zhuǎn)、左右翻轉(zhuǎn))的相關(guān)資料,需要的朋友可以參考下
    2017-05-05
  • C++實(shí)現(xiàn)LeetCode(20.驗(yàn)證括號(hào))

    C++實(shí)現(xiàn)LeetCode(20.驗(yàn)證括號(hào))

    這篇文章主要介紹了C++實(shí)現(xiàn)LeetCode(20.驗(yàn)證括號(hào)),本篇文章通過簡要的案例,講解了該項(xiàng)技術(shù)的了解與使用,以下就是詳細(xì)內(nèi)容,需要的朋友可以參考下
    2021-07-07
  • C++實(shí)現(xiàn)各種排序算法類匯總

    C++實(shí)現(xiàn)各種排序算法類匯總

    這篇文章主要介紹了C++實(shí)現(xiàn)各種排序算法類,需要的朋友可以參考下
    2014-07-07
  • C++實(shí)現(xiàn)動(dòng)態(tài)規(guī)劃過程詳解

    C++實(shí)現(xiàn)動(dòng)態(tài)規(guī)劃過程詳解

    動(dòng)態(tài)規(guī)劃是解決一類最優(yōu)問題的常用方法,它是解決最優(yōu)化問題的一種途徑,在本文中,我們將討論如何使用C++實(shí)現(xiàn)動(dòng)態(tài)規(guī)劃算法,并提供一些示例來幫助您更好地理解該算法
    2023-05-05
  • C++智能指針讀書筆記

    C++智能指針讀書筆記

    本篇隨筆僅作為個(gè)人學(xué)習(xí)《C++ Primer》智能指針一節(jié)后的部分小結(jié),抄書嚴(yán)重,伴隨個(gè)人理解。主要介紹shared_ptr、make_shared、weak_ptr的用法和聯(lián)系
    2015-11-11
  • C語言實(shí)現(xiàn)電話簿項(xiàng)目管理

    C語言實(shí)現(xiàn)電話簿項(xiàng)目管理

    這篇文章主要為大家詳細(xì)介紹了C語言實(shí)現(xiàn)電話簿項(xiàng)目管理,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2021-07-07

最新評(píng)論