小根堆的解法。一定要注意边界的处理。忽略了几处的边界处理居然可以通过10个用例
1. 初始化堆,自底向上初始化,如果发生了交换,就要该节点自顶向下交换
2. 每次调整选中一个最小的,放入list
import java.util.ArrayList;
public class Solution {
private void swap(int[] input, int i, int j) {
int t = input[i];
input[i] = input[j];
input[j] = t;
}
private void initHeap(int[] input) {
int length = (input.length - 1) / 2;
// 边界条件 i >= length,不能忽略
for (int i = input.length - 1; i >= length; i--) {
int j = i;
while (j != 0) {
int parent = (j-1)/2;
if (input[j] < input[parent]) {
swap(input, j, parent);
// 向下调整
adjust(input, parent, input.length - 1);
}
j = parent;
}
}
}
private void adjust(int[] input, int start, int length) {
if (length == 0) {
return;
}
while (start <= (length - 1) / 2) {
int left = 2 * start + 1;
int right = 2 * start + 2;
int minIndex = left;
// 这里一定要小于等于
if(right <= length) {
minIndex = input[left] < input[right] ? left : right;
}
if (input[minIndex] < input[start]) {
swap(input, minIndex, start);
}
start = minIndex;
}
}
public ArrayList<Integer> GetLeastNumbers_Solution(int [] input, int k) {
ArrayList<Integer> list = new ArrayList<Integer>();
if (k <= 0) {
return list;
}
initHeap(input);
list.add(input[0]);
swap(input, 0, input.length - 1);
for(int i = 1; i < k; i++) {
adjust(input, 0, input.length - i - 1);
list.add(input[0]);
swap(input, 0, input.length - 1 - i);
}
return list;
}
}

京公网安备 11010502036488号