1.堆

1.堆结构就是用数组实现的完全二叉树结构
2.完全二叉树中如果每颗子树的最大值都在顶部就是大根堆
3.完全二叉树中如果每颗子树的最小值都在顶部就是小根堆
4.堆结构的heapInsert与heapify操作
5.堆结构的增大与减少
6.优先级队列结构,就是堆结构
二叉树:image.png size:7 i位置的左孩子:(i2+1) i位置的右孩子 (i 2 + 2) i的父位置:i-1/2
从0出发 由size说明是连续的几个数,就可以看成是完全二叉树。

堆操作的两个调整:heapInsert、heapify。
heapInsert代码:

  1. public class heapInsert {
  2. public static void heapInsert(int[] arr, int index) {
  3. while (arr[index] > arr[(index-1)/2]) {
  4. sawp(arr, index, (index - 1) / 2);
  5. index = (index - 1) / 2;
  6. }
  7. }
  8. }

heapify代码:

  1. public class heapify {
  2. public static void heapify(int[] arr, int index, int heapSize){
  3. int left = index * 2 + 1; // 左孩子的下标
  4. while(left < heapSize){ // 下方还有孩子
  5. // 两个孩子中,谁的值大,把下标给largest
  6. int largest = left + 1 < heapSize && arr[left + 1] > arr[left]
  7. ? left + 1 : left;
  8. // 父和孩子之间,谁的值大,把下标给largest
  9. largest = arr[largest] > arr[index] ? largest : index;
  10. if(largest == index){
  11. break;
  12. }
  13. swap(arr, largest, index);
  14. index = largest;
  15. left = index * 2 + 1;
  16. }
  17. }
  18. }

完全二叉树的高度: logN级别。

2.堆排序

  1. public class heapSort {
  2. public static void heapSort(int[] arr){
  3. if(arr == null || arr.length == 2){
  4. return;
  5. }
  6. // for(int i = 0; i < arr.length; i++){
  7. // heapInsert(arr, i);
  8. // }
  9. // 如果只是单纯的将一个数组拼成大根堆用下边的算法更好
  10. for(int i = arr.length -1; i >= 0; i--){
  11. heapify(arr, i, arr.length);
  12. }
  13. int heapSize = arr.length;
  14. swap(arr, 0, --heapSize);
  15. while(heapSize > 0){
  16. heapify(arr, 0, heapSize);
  17. swap(arr, 0, --heapSize);
  18. }
  19. }
  20. public static void heapInsert(int[] arr, int index) {
  21. while (arr[index] > arr[(index-1)/2]) {
  22. swap(arr, index, (index - 1) / 2);
  23. index = (index - 1) / 2;
  24. }
  25. }
  26. public static void heapify(int[] arr, int index, int heapSize){
  27. int left = index * 2 + 1; // 左孩子的下标
  28. while(left < heapSize){ // 下方还有孩子
  29. // 两个孩子中,谁的值大,把下标给largest
  30. int largest = left + 1 < heapSize && arr[left + 1] > arr[left]
  31. ? left + 1 : left;
  32. // 父和孩子之间,谁的值大,把下标给largest
  33. largest = arr[largest] > arr[index] ? largest : index;
  34. if(largest == index){
  35. break;
  36. }
  37. swap(arr, largest, index);
  38. index = largest;
  39. left = index * 2 + 1;
  40. }
  41. }
  42. public static void swap(int[] arr, int x, int y) {
  43. int temp = arr[x];
  44. arr[x] = arr[y];
  45. arr[y] = temp;
  46. }
  47. }