题目描述:
题目来自(牛客网)
最小的K个数
参与人数:5221时间限制:1秒空间限制:32768K
输入n个整数,找出其中最小的K个数。例如输入4,5,1,6,2,7,3,8这8个数字,则最小的4个数字是1,2,3,4,。
解析:
根据题意,读者首先想到的是进行排序(小-大),提取前k个数字。这次为了复习一下快速排序,采用了快排序,看似快速排序比较复杂,但是在牛客网测试,总运行时间竟然用的比冒泡还要短(不太理解为什么了!)。
1.快速排序实现
快速排序分为2个部分
- 一趟快速排序:取某一个记录作为标准值(通常取第一个值),通过一趟排序将待排序的记录分为小于或等于这个标准值和大于这个标准值的两个独立的部分
- 递归实现:
- -
//需求
public ArrayList<Integer> GetLeastNumbers_Solution(int [] input, int k) {
ArrayList<Integer> arrayList = new ArrayList<Integer>();
int[] out = new Solution().quickSort(input,0,input.length-1);
if(k>input.length){
return arrayList;
}else
for(int i=0;i<k;i++)
arrayList.add(out[i]);
return arrayList;
}
//递归过程
public int[] quickSort(int[] array,int low,int high){
if(low<high){
int temp = quickPartition(array,low,high);
quickSort(array,low,temp-1);
quickSort(array,temp+1,high);
}
return array;
}
//一趟排序之后,小于键值的在左边,大于键值的在右边。
public int quickPartition(int[] R,int low,int high){
int x = R[low];
while(low<high){
//自尾端进行比较,找到第一个比x值小的元素,获得位标
while(low<high&&R[high]>=x){
high --;
}
R[low] = R[high];//小元素会跑到键值位置;
//自开始端进行比较,找到第一个比x大的元素,获得位标
while(low<high&&x>=R[low]){
low ++;
}
R[high] = R[low];
//大元素会跑到后面去
}
R[low] = x;
return low;
}
2.冒泡排序
public ArrayList<Integer> GetLeastNumbers_Solution2(int [] input, int k) {
ArrayList<Integer> arrayList = new ArrayList<Integer>();
int temp;
if(k>input.length)
return arrayList;
//冒泡排序的思想:遍历所有元素,找最小的元素,冒泡的顶部。i<k就是找到总共k个最小元素,看起来就简单很多了
for(int i=0;i<k;i++){
for(int j=i+1;j<input.length;j++){
if(input[j]<input[i]){
temp = input[j];
input[j] = input[i];
input[i] = temp;
}
}
arrayList.add(input[i]);
}
return arrayList;
}