1. 程式人生 > 其它 >Java通過JDBC實現資料庫的連線

Java通過JDBC實現資料庫的連線

堆的應用比較多,比如堆排序等等,下面就來介紹下堆

堆是一棵樹(完全二叉樹)的形式,其每個結點都有一個值,且每個結點的值都大於/小於等於其父結點的值

  • 小根堆:每個結點的值都大於等於其父結點的值
  • 大根堆:每個結點的值都小於等於其父結點的值

注意:堆的根結點存放的是最大值或者最小值,但其他結點的值的排序是未知的,這與二叉搜尋樹不同

堆的基本操作

  • 插入一個數

    在末尾插入新的元素,然後向上調整

  • 求堆中的最小(大)值

    返回堆頂元素

  • 刪除最小值

    用末尾的元素去覆蓋堆頂元素,然後再將堆頂元素向下調整

  • 刪除任意一個元素

    將任意一個元素覆蓋堆頂元素,然後再將堆頂元素向下或者向上調整

  • 修改任意一個元素

    直接賦值,再將該元素向上或者向下調整

const int N = 100010;
int heap[N],l;

void down(int x) {
  //用t來代表根結點和其左右兒子中的最小值的下標
  int t = x;
  //如果左兒子存在且左兒子小於t,則t等於左兒子
  if (x * 2 <= l && heap[x * 2] < heap[t]) {
   	 t = x * 2; 
  }
  if (x * 2 + 1 <= l && heap[x * 2 + 1] < heap[t]) {
    t = x * 2 + 1;
  }
  //當根結點不是最小值的時候
  if (x != t) {
    swap(heap[t],heap[x]);
    down(t);
  }
}

void up(int x) {
  //當該點有父結點且該點的值大於其父結點的值,則進行交換
  while (x/2 > 0 && heap[x/2] > h[x]) {
    swap(heap[x/2],heap[x]);
    x /= 2;
  }
}

//最小值
heap[1];

//刪除最小元素
heap[1] = heap[l];
l--;
down(1);

解釋:為何刪除元素時需要覆蓋堆頂元素,再調整

由於我們使用陣列儲存堆,在陣列中,刪除第一個元素比較困難,但刪除最後一個元素比較簡單,我們只需要用最後一個元素覆蓋掉第一個元素,這樣一來,最後一個元素還儲存在陣列中,只是位置變了,而要刪除的元素已經不在了,此時我們使陣列的長度減一,再將第一個元素進行排序,調整到合適的位置即可

堆的儲存方式

我們採用陣列的方式去實現堆

下標從1開始時:

  • x的左兒子:2 * x
  • x的右兒子:2 * x + 1

堆的建立

我們在陣列儲存了所有的元素後,需要建堆,此時我們一般採用一種O(n)的方法來實現

以小根堆為例,我們從n/2處的元素開始執行向下調整(down)操作

for (int i = n/2;i > 0; i--) {
  down(i);
}

解釋:因為n/2是堆的倒數第二層,所以我們將上面的所有元素都進行一個下沉操作來維護堆的有序

STL中的堆

c++中,提供了一個優先佇列,實現堆的功能

priority_queue自動實現排序

//大根堆
priority_queue<int> heap;
//小根堆
priority_queue<int,vector<int>,greater<int>> heap;

//返回堆頂元素
heap.top();
//向堆插入一個數
heap.push(1);
//彈出堆頂元素
heap.pop();
//判斷堆是否為空
heap.empty();
//返回元素個數
heap.size();