Offer prove safety fluent flow series such as - the smallest number k

40 is inscribed: smallest number k

One, Title Description

Input n integers, find the smallest number k. 4,5,1,6,2,7,3,8 e.g. eight digital inputs, the minimum number is four 1,2,3,4.

Second, the problem analysis

The method of sorting is most likely to occur, to take the corresponding element numbers (note de-emphasis). I am here for the convenience of direct use of the fast row to do this deduplication, you can use the Set collection to do the heavier, more convenient and more efficient.

When, traversing integer n, k smallest digital storage with a container, when confronted with the largest number smaller than the container numbers: to widen the gap with others, will inevitably need to optimize time efficiency, we can do this is replaced with the maximum number. You can use a maximum heap container or red-black tree to achieve. Heap compared to red-black tree is easier to implement, we here adopt the heap.

Third, questions

A thought (not recommended)

    public ArrayList<Integer> GetLeastNumbers(int [] input, int k) {
        ArrayList<Integer> leastNumbers = new ArrayList<>();
        if(input==null || k<=0 || k>input.length) {
            return leastNumbers;
        }

        int start=0;
        int end=input.length-1;
        int index=partition(input,start,end);

        while(index!= k-1){
            if(index< k-1){
                start=index+1;
                index=partition(input,start,end);
            }else{
                end=index-1;
                index=partition(input,start,end);
            }
        }
        for(int i=0;i<k;i++){
            leastNumbers.add(input[i]);
        }
        return leastNumbers;
    }

    private int partition(int[] arr, int start,int end){
        int pivotKey=arr[start];
        while(start<end){
            while(start<end && arr[end]>=pivotKey) {
                end--;
            }
            swap(arr,start,end);
            while(start<end && arr[start]<=pivotKey){
                start++;
            }
            swap(arr,start,end);
        }
        return start;
    }

    private void swap(int[] arr, int i,int j){
        int temp=arr[i];
        arr[i]=arr[j];
        arr[j]=temp;
    }

Thinking two (recommended)

  public ArrayList<Integer> GetLeastNumbers(int [] input, int k) {
        ArrayList<Integer> leastNumbers = new ArrayList<>();
        if(input==null || k<=0 || k>input.length) {
            return leastNumbers;
        }
        int[] numbers=new int[k];  //用于放最小的k个数
        //先放入前k个数
        System.arraycopy(input, 0, numbers, 0, k);

        for(int i = k/2-1; i>=0; i--){
            adjustHeap(numbers,i,k-1);//将数组构造成最大堆形式
        }
        for(int i = k; i<input.length; i++){
            if(input[i]<numbers[0]){ //存在更小的数字时
                numbers[0]=input[i];
                adjustHeap(numbers,0,k-1);//重新调整最大堆
            }
        }
        for(int n:numbers)
            leastNumbers.add(n);
        return leastNumbers;
    }

    //最大堆的调整方法
    private void adjustHeap(int[] arr,int start,int end){
        int temp=arr[start];
        int child=start*2+1;
        while(child<=end){
            if(child+1<=end && arr[child+1]>arr[child]) {
                child++;
            }
            if(arr[child]<temp) {
                break;
            }
            arr[start]=arr[child];
            start=child;
            child=child*2+1;
        }
        arr[start]=temp;
    }
Published 158 original articles · won praise 3221 · Views 460,000 +

Guess you like

Origin blog.csdn.net/qq_42322103/article/details/104109944