中文亚洲精品无码_熟女乱子伦免费_人人超碰人人爱国产_亚洲熟妇女综合网

當前位置: 首頁 > news >正文

網(wǎng)站流量站怎么做百度下載官網(wǎng)

網(wǎng)站流量站怎么做,百度下載官網(wǎng),東營網(wǎng)站建設哪家好,wordpress 圖片連接插件引言 什么是堆?堆是一種特殊的數(shù)據(jù)結構(用數(shù)組表示的樹)。 為什么要使用到堆?比如一場比賽,如果使用擂臺賽的方式來決出冠軍(實力第一),就很難知道實力第二的隊伍是什么了。 但是…

引言

什么是堆?堆是一種特殊的數(shù)據(jù)結構(用數(shù)組表示的樹)。

為什么要使用到堆?比如一場比賽,如果使用擂臺賽的方式來決出冠軍(實力第一),就很難知道實力第二的隊伍是什么了。

但是下圖能很清楚的表示各隊伍的強弱關系。

堆的特點

上圖就是一個最大堆,解釋:每一個圓都是一個節(jié)點,數(shù)字代表著鍵值,其中95是93和92的父節(jié)點,93和92是95的子節(jié)點,93和92是兄弟節(jié)點(父節(jié)點為同一個),根節(jié)點就是鍵值最大的節(jié)點,為95,最后一個節(jié)點是87,最后一個左子節(jié)點也是87。

最大堆的特點

滿足以下三點

1.每個節(jié)點最多可以有兩個子節(jié)點。

2.根節(jié)點的鍵值是所有堆節(jié)點鍵值中最大者,且每個節(jié)點的值都大于其子(孩子)節(jié)點。

3.除了根節(jié)點沒有兄弟節(jié)點,最后一個左子節(jié)點可以沒有兄弟節(jié)點,其他節(jié)點必須有兄弟節(jié)點。

最好是自己理解,不用強記 。其中有一點要注意:A的兄弟節(jié)點的子節(jié)點可能大于A,相當于在比賽中,其中一個小組都是弱隊,那么一個弱隊卻可以闖入半決賽一樣。

最小堆的特點的話就將第二點中的大改為小就可以了,其他的特點一樣。這里討論的是最大堆

數(shù)組形式表示

父節(jié)點和子節(jié)點的關系:

i 的左子節(jié)點:2i+1 ,右子節(jié)點:2i+2

i 的父節(jié)點:(i-1)/2

i 是從 0 開始的

再將上圖的堆轉(zhuǎn)換為數(shù)組的形式,如下圖:

?這就是一個最大堆的數(shù)組表示形式。

在數(shù)組中快速創(chuàng)建堆

也就是怎么把任意一個數(shù)組變成最大/小堆。

我們先把堆的最小單位拿出來,如下圖:

他不是一個最大堆,如果要變成最大堆,只需要父節(jié)點是95,子節(jié)點分別是86、88就可以了(86和95交換)。而一個最大堆是由若干個這個最小單位組成的,所以第一步就是將所有的堆的最小單位變成最大堆。

1、首先先找到最后一個節(jié)點的父節(jié)點,找出該節(jié)點的最大子節(jié)點與自己比較,如果大于自身,就交換兩個節(jié)點。

2、繼續(xù)移動到上一個父節(jié)點(也就是下標 -1 的地方),重復做第一步的比較操作,直到遍歷所有的父節(jié)點。

當我們移動完所有的父節(jié)點,那最大堆就形成了嗎?還疏忽了一個地方。例如當移動到某個父節(jié)點時,如下圖:

最開始父節(jié)點是88,與子節(jié)點95交換了,那父節(jié)點就是95,95 的子節(jié)點就是 88,那88一定大于他的子節(jié)點嗎?很顯然這個答案是不一定,因為 88 的子節(jié)點只滿足小于之前的父節(jié)點 95,所以還需要向下調(diào)整,直到子節(jié)點都小于父節(jié)點。

3、對每次移動中,變成子節(jié)點的節(jié)點,向下調(diào)整,也就是判斷他與子節(jié)點是否滿足最大堆的特點,不滿足還要繼續(xù)移動節(jié)點(向下調(diào)整),滿足的話就接著下個父節(jié)點。

4、所有的節(jié)點交換完畢,最大堆構建完成。

堆的算法實現(xiàn)

堆數(shù)據(jù)結構的定義

#define DEFAULT_CAPCITY 120 //默認的堆容量typedef struct _Heap
{int* arr;		//存儲堆元素的數(shù)組int size;		//堆中元素的個數(shù)int capcity;	//堆的容量
}Heap;//函數(shù)聲明
void buildHeap(Heap& heap);
bool inset(Heap& heap, int value);
bool initHeap(Heap& heap, int* orginal, int size);
void adjustDown(Heap& heap, int i);
void adjustUp(Heap& heap, int i);

堆的初始化?

bool initHeap(Heap& heap,int *orginal,int size) 
{//orginal 是指向數(shù)組的指針,而這個數(shù)組是我們要傳入堆的數(shù)組int capcity = DEFAULT_CAPCITY > size ? DEFAULT_CAPCITY : size; //取size和默認容量的最大值heap.arr = new int[capcity];if (!heap.arr) return false; //申請失敗heap.capcity = capcity;if (size > 0) //size合法{memcpy(heap.arr, orginal, sizeof(int) * size);heap.size = size;//建堆buildHeap(heap);}return true;
}

堆的創(chuàng)建

//建堆,從最后一個父節(jié)點逐個向前調(diào)整所有的父節(jié)點(直到根節(jié)點),確保每一個父節(jié)點都是一個最大堆
//那么,整體上就是一個最大堆
void buildHeap(Heap& heap)
{int i = (heap.size - 2) / 2; //因為下標從0開始,heap.size-1就得到下標,再結合公式就是這個式子for (; i >= 0; i--){adjustDown(heap, i); //向下調(diào)整包含了構建最大堆,如果感到困惑,先看向下調(diào)整函數(shù)}
}

堆的向下調(diào)整函數(shù)

void adjustDown(Heap& heap, int i)
{int temp = heap.arr[i]; //保存父節(jié)點的鍵值int parent = 0 ,child = 0;for (parent = i; (2 * parent + 1) < heap.size; parent = child) {child = 2 * parent + 1; //先指向左子節(jié)點//指向兩個子節(jié)點中最大的節(jié)點if (child + 1 < heap.size && heap.arr[child] < heap.arr[child + 1]){child = child + 1;}if (temp >= heap.arr[child]){break; //無需向下調(diào)整}else{heap.arr[parent] = heap.arr[child];heap.arr[child] = temp;}}
}

堆的插入新元素

1、插入新的元素到最大堆的尾部,也就是數(shù)組的后面

2、插入的元素可能會破環(huán)這個最大堆,需要重新調(diào)整,和父節(jié)點比較,如果比父節(jié)點大,就交換兩個節(jié)點……重復直到新節(jié)點比父節(jié)點小或者新節(jié)點變?yōu)楦?jié)點(調(diào)整到位)。

設計兩個函數(shù),一個是插入,一個是向上調(diào)整。

bool insert(Heap& heap, int value)
{if (heap.size == heap.capcity) //堆空間不足{return false;}int i = heap.size ; //指向新加元素的下標heap.arr[heap.size++] = value;adjustUp(heap , i);return true;
}
void adjustUp(Heap& heap, int i)
{if (i <= 0 || i >= heap.size) return;while (i > 0){int parent = (i - 1) / 2;if (parent >= 0) // 父節(jié)點沒越界{if (heap.arr[parent] < heap.arr[i]){int temp = heap.arr[i];heap.arr[i] = heap.arr[parent];heap.arr[parent] = temp;i = parent;}else{break; //無需調(diào)整}}else{break; //父節(jié)點出界}}
}

看到這,你會發(fā)現(xiàn)堆的創(chuàng)建還有一種方式,也就是將數(shù)組的元素一個一個插入,也能得到最大堆。

源代碼

#include <iostream>using namespace std;#define DEFAULT_CAPCITY 120 //默認的堆容量typedef struct _Heap
{int* arr;		//存儲堆元素的數(shù)組int size;		//堆中元素的個數(shù)int capcity;	//堆的容量
}Heap;void buildHeap(Heap& heap);
bool insert(Heap& heap, int value);
bool initHeap(Heap& heap, int* orginal, int size);
void adjustDown(Heap& heap, int i);
void adjustUp(Heap& heap, int i);//初始化堆
bool initHeap(Heap& heap,int *orginal,int size) 
{//orginal 是指向數(shù)組的指針,而這個數(shù)組是我們要傳入堆的數(shù)據(jù)int capcity = DEFAULT_CAPCITY > size ? DEFAULT_CAPCITY : size; //取size和默認容量的最大值heap.arr = new int[capcity];if (!heap.arr) return false;heap.capcity = capcity;if (size > 0){memcpy(heap.arr, orginal, sizeof(int) * size);heap.size = size;//建堆buildHeap(heap);}return true;
}//建堆,從最后一個父節(jié)點逐個向前調(diào)整所有的父節(jié)點(直到根節(jié)點),確保每一個父節(jié)點都是一個最大堆
//那么,整體上就是一個最大堆
void buildHeap(Heap& heap)
{int i = (heap.size - 2) / 2; //因為下標從0開始,heap.size-1就得到下標for (; i >= 0; i--){adjustDown(heap, i);}
}void adjustDown(Heap& heap, int i)
{int temp = heap.arr[i]; //父節(jié)點的鍵值int parent = 0 ,child = 0;for (parent = i; (2 * parent + 1) < heap.size; parent = child){child = 2 * parent + 1;//指向兩個子節(jié)點中最大的節(jié)點if (child + 1 < heap.size && heap.arr[child] < heap.arr[child + 1]){child = child + 1;}if (temp >= heap.arr[child]){break; //無需向下調(diào)整}else{heap.arr[parent] = heap.arr[child];heap.arr[child] = temp;}}
}//堆——插入新元素
bool insert(Heap& heap, int value)
{if (heap.size == heap.capcity){return false;}int i = heap.size ;heap.arr[heap.size++] = value;adjustUp(heap , i);return true;
}void adjustUp(Heap& heap, int i)
{if (i <= 0 || i >= heap.size) return;while (i > 0){int parent = (i - 1) / 2;if (parent >= 0) // 父節(jié)點沒越界{if (heap.arr[parent] < heap.arr[i]){int temp = heap.arr[i];heap.arr[i] = heap.arr[parent];heap.arr[parent] = temp;i = parent;}else{break; //無需調(diào)整}}else{break; //父節(jié)點出界}}
}
int main(void)
{Heap heap;int orginalArr[] = { 1,2,3,87,93,82,92,86,95 };if (!initHeap(heap, orginalArr, sizeof(orginalArr) / sizeof(int))){cout << "初始化堆失敗!" << endl;exit(-1);}for (int i = 0; i < heap.size; i++){printf("%d\n",heap.arr[i]);}puts("");insert(heap, 100);for (int i = 0; i < heap.size; i++){printf("%d\n", heap.arr[i]);}return 0;
}
http://www.risenshineclean.com/news/30982.html

相關文章:

  • 重慶網(wǎng)站建設推廣seo網(wǎng)站排名助手
  • 做JAVA基礎編程題什么網(wǎng)站好汕頭seo排名
  • 網(wǎng)站項目案例自動搜索關鍵詞軟件
  • 杭州電子商務網(wǎng)站建設百度指數(shù)分析案例
  • 新農(nóng)村建設 網(wǎng)站google 網(wǎng)站推廣
  • 有哪些網(wǎng)站建設工作本周新聞熱點
  • 做彩票生意要登陸哪個網(wǎng)站百度怎么做推廣和宣傳
  • icp備案網(wǎng)站建設方案書網(wǎng)站收錄一般多久
  • 阿克蘇建設租房信息阿克蘇租房網(wǎng)站磁力搜索器
  • 破解php網(wǎng)站后臺賬號密碼朋友圈廣告推廣文字
  • 寧波商城網(wǎng)站建設淘寶指數(shù)查詢官網(wǎng)
  • 網(wǎng)站訪問量大 處理小程序如何推廣運營
  • 免費開店鋪網(wǎng)站關鍵字優(yōu)化價格
  • 織夢后臺做的網(wǎng)站怎么綁定域名湖南網(wǎng)站建設營銷推廣
  • 做網(wǎng)站字體格式用銳利嗎即刻搜索引擎入口
  • 成都游戲網(wǎng)站開發(fā)代發(fā)關鍵詞排名包收錄
  • 做網(wǎng)站 流量怎么抓錢網(wǎng)推廣公司
  • 無錫建設網(wǎng)站的公司湖南百度seo
  • 無錫兼職做網(wǎng)站電商培訓內(nèi)容
  • 徐州提供網(wǎng)站建設報價表寧波seo網(wǎng)絡推廣優(yōu)化價格
  • 動態(tài)網(wǎng)站開發(fā)平臺簡介什么叫seo
  • 購物網(wǎng)站策劃案廈門谷歌seo公司
  • 北京網(wǎng)站建設的價格中國最好的營銷策劃公司
  • 做班級的活動的網(wǎng)站企業(yè)營銷策劃方案范文
  • 招聘H5在什么網(wǎng)站做最好搜索引擎排名
  • 用手機什么軟件做網(wǎng)站百度推廣怎么操作流程
  • 帶登錄網(wǎng)站模板網(wǎng)站建設的整體流程有哪些
  • 阿里云Windows網(wǎng)站建設廣東百度推廣的代理商
  • 自助建站系統(tǒng)免授權版企業(yè)查詢網(wǎng)
  • 網(wǎng)站開發(fā)專業(yè)就業(yè)培訓學校石家莊網(wǎng)絡營銷網(wǎng)站推廣