剑指offer第二九题。
题目描述
输入n个整数,找出其中最小的K个数。例如输入4,5,1,6,2,7,3,8这8个数字,则最小的4个数字是1,2,3,4。
解题思路
对于这种不变的数组,第一种思路是快速排序,然后找出前几个数即可,这种方法的时间复杂度为nlogn。
第二种更优的思路是堆排,因为找到前k个数字的时间复杂度为nlogk
我的答案
快速排序:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56
| import java.util.ArrayList; public class Solution { public ArrayList<Integer> GetLeastNumbers_Solution(int [] input, int k) { ArrayList<Integer> res = new ArrayList<>(); if(k > input.length || k == 0){ return res; } quick_sort(input,0,input.length-1); for(int i=0;i<k;i++){ res.add(input[i]); } return res; } private void quick_sort(int[] arr,int low,int high){ if(low < high){ int[] p = partion(arr,low,high); quick_sort(arr,low,p[0]-1); quick_sort(arr,p[1]+1,high); } } private int[] partion(int[] arr,int low,int high){ int less = low - 1; int more = high + 1; int curr = low; int num = arr[curr]; while(curr < more){ if(arr[curr] < num){ swap(arr,++less,curr++); }else if(arr[curr] > num){ swap(arr,curr,--more); }else{ curr++; } } return new int[]{less,more}; } private void swap(int[] arr, int i, int j) { int tmp = arr[i]; arr[i] = arr[j]; arr[j] = tmp; } }
|
原生堆排来实现:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86
| import java.util.ArrayList; public class Solution { ArrayList<Integer> res = new ArrayList<>(); public ArrayList<Integer> GetLeastNumbers_Solution(int [] input, int k) { if(k == 0 || k > input.length){ return res; } heapSort(input,k); return res; } private void heapSort(int[] arr,int k){ if(arr == null || arr.length < 2){ return; } for(int i=0;i<arr.length;i++){ heapInsert(arr,i); } int heapSize = arr.length; swap(arr,0,--heapSize); res.add(arr[heapSize]); if(res.size() == k){ return; } while(heapSize > 0){ heapify(arr,0,heapSize); swap(arr,0,--heapSize); res.add(arr[heapSize]); if(res.size() == k){ return; } } } private void heapInsert(int[] arr,int i){ while(arr[i] < arr[(i-1)/2]){ swap(arr,i,(i-1)/2); i = (i-1)/2; } } private void heapify(int[] arr,int index,int heapSize){ int left = index * 2 + 1; while(left < heapSize){ int largest = left+1 < heapSize && arr[left+1]<arr[left] ? left+1 : left; int maxIndex = arr[index] < largest ? index : largest; if(maxIndex == index){ break; } swap(arr,index,largest); index = maxIndex; left = index * 2 + 1; } } private void swap(int[] arr, int i, int j) { int tmp = arr[i]; arr[i] = arr[j]; arr[j] = tmp; } }
|