方法一:用partition来做,把之前求中位数的方法,类似用到这个题上,只是求的不是中位数,而是排序后的第k-1的位置,注意边界
import java.util.ArrayList;
public class Solution {
public ArrayList<Integer> GetLeastNumbers_Solution(int [] input, int k) {
ArrayList<Integer> al=new ArrayList<Integer>();
if(input.length<k||k==0)
return al;
int s=0,e=input.length-1;
int p=partition(input,s,e);
while(p!=k-1){
if(p<k-1){
s=p+1;
p=partition(input,s,e);
}
else{
e=p-1;
p=partition(input,s,e);
}
}
for(int i=0;i<k;i++){
al.add(input[i]);
}
return al;
}
public int partition(int[] arr,int start,int end){
int p=end;
int i=start-1,j=end;
while(true){
while(arr[++i]<arr[p]);
while(j>0&&arr[--j]>arr[p]);
if(i<j)
swap(arr,i,j);
else
break;
}
swap(arr,i,p);
return i;
}
public void swap(int[] arr,int i,int j){
int temp=arr[i];
arr[i]=arr[j];
arr[j]=temp;
}
}
方法二:利用TreeSet,它实现了红黑树的查找,它的查找、删除和插入操作时间复杂度都是O(logk),这个方法不用改变输入数组,适用于海量数据(内存有限时,可以分批次读入),但是时间会稍微长一点,上面那个方法大概17ms,这个方法大概26ms,代码如下
import java.util.ArrayList;
import java.util.TreeSet;
public class Solution {
public ArrayList<Integer> GetLeastNumbers_Solution(int [] input, int k) {
ArrayList<Integer> a=new ArrayList<Integer>();
if(k>input.length||k==0)
return a;
TreeSet<Integer> ti=new TreeSet<Integer>();
for(int i=0;i<input.length;i++){
if(ti.size()<k){
ti.add(input[i]);
}
else{
//注意TreeSet的几种用法
if(ti.ceiling(input[i])!=null){
ti.pollLast();
ti.add(input[i]);
}
else;
}
}
//注意addAll添加的是Collection
a.addAll(ti);
return a;
}
}