|
10 | 10 | * 以求top k大为例
|
11 | 11 | * @param arr
|
12 | 12 | */
|
13 |
| - //region bf解法 |
14 | 13 | function topK(arr, k) {
|
15 |
| - let index = bfprt(arr, 0, arr.length - 1, k), |
16 |
| - res = arr.slice(0, index + 1); |
17 |
| - console.log(`原数组:${arr}`); |
18 |
| - console.log(`前${k}大元素:${res}`) |
| 14 | + let bfArr = arr.slice(0), |
| 15 | + heapArr = arr.slice(0); |
| 16 | + //bf solution |
| 17 | + let bfindex = bfprt(arr, 0, bfArr.length - 1, k), |
| 18 | + ret1 = arr.slice(0, bfindex + 1); |
| 19 | + |
| 20 | + console.log(`bf solution: 前${k}大元素:${ret1}`); |
| 21 | + |
| 22 | + //heap solution |
| 23 | + let heap = new indexMaxHeap(heapArr), |
| 24 | + ret2 = []; |
| 25 | + for (let i = 0; i < k; i++) { |
| 26 | + ret2.push(heap.extractMax()) |
| 27 | + } |
| 28 | + console.log(`heap solution: 前${k}大元素:${ret2}`) |
| 29 | + |
19 | 30 | }
|
20 | 31 |
|
| 32 | + //region bf solution |
21 | 33 | let bfprt = function (arr, l, r, k) {
|
22 | 34 | let central_index = getCentralIndex(arr, l, r),
|
23 | 35 | boundary_index = partition(arr, l, r, central_index),
|
|
75 | 87 | };
|
76 | 88 | //endregion
|
77 | 89 |
|
| 90 | + //region heap solution |
| 91 | + class indexMaxHeap { |
| 92 | + constructor(arr) { |
| 93 | + this.data = []; |
| 94 | + this.indexes = []; |
| 95 | + this.reverse = []; |
| 96 | + this.count = 0; |
| 97 | + for (let i = 0; i < arr.length; i++) { |
| 98 | + this.insert(i, arr[i]) |
| 99 | + } |
| 100 | + |
| 101 | + } |
| 102 | + |
| 103 | + insert(i, value) { |
| 104 | + this.data[++i] = value; |
| 105 | + this.indexes[++this.count] = i; |
| 106 | + this.reverse[i] = this.count; |
| 107 | + this.shiftUp(this.count) |
| 108 | + |
| 109 | + } |
| 110 | + |
| 111 | + shiftUp(k) { |
| 112 | + while (k > 1 && this.data[this.indexes[k]] > this.data[this.indexes[k >> 1]]) { |
| 113 | + this.swapIndex(k, k >> 1) |
| 114 | + k = k >> 1 |
| 115 | + } |
| 116 | + } |
| 117 | + |
| 118 | + shiftDown(k) { |
| 119 | + while (2 * k <= this.count) { |
| 120 | + let j = 2 * k; |
| 121 | + if (j + 1 <= this.count - 1 && this.data[this.indexes[j + 1]] > this.data[this.indexes[j]]) { |
| 122 | + j += 1; |
| 123 | + } |
| 124 | + if (this.data[this.indexes[k]] >= this.data[this.indexes[j]]) return; |
| 125 | + |
| 126 | + this.swapIndex(k, j) |
| 127 | + k = j; |
| 128 | + } |
| 129 | + } |
| 130 | + |
| 131 | + extractMax() { |
| 132 | + let res = this.data[this.indexes[1]]; |
| 133 | + this.swapIndex(1, this.count); |
| 134 | + this.reverse[this.indexes[this.count]] = 0; |
| 135 | + this.count--; |
| 136 | + this.shiftDown(1); |
| 137 | + return res |
| 138 | + } |
| 139 | + |
| 140 | + swapIndex(i, j) { |
| 141 | + [this.indexes[i], this.indexes[j]] = [this.indexes[j], this.indexes[i]] |
| 142 | + |
| 143 | + this.reverse[this.indexes[i]] = i; |
| 144 | + this.reverse[this.indexes[j]] = j |
| 145 | + |
| 146 | + } |
| 147 | + } |
| 148 | + |
| 149 | + //endregion |
| 150 | + |
78 | 151 | topK([32, 153, 100, -50, -10, 6, 5, 1356, 20, 160, 2, 1432, 4, 50, 14, 102, -30, 3, 45, 1312, 1, -1, -3], 7)
|
79 | 152 | </script>
|
80 | 153 | </body>
|
|
0 commit comments