LeetCode每日一题:数组中的第 K 个最大元素

题目:

在未排序的数组中找到第 k 个最大的元素。请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素。

示例 1:

输入: [3,2,1,5,6,4] 和 k = 2
输出: 5
示例 2:

输入: [3,2,3,1,2,4,5,5,6] 和 k = 4
输出: 4
说明:你可以假设 k 总是有效的,且 1 ≤ k ≤ 数组的长度。

方法一:排序

算法:

1、对数组进行从小到大排序;

2、将数组按从大到小的顺序入队;

3、将第k个元素出队返回;

代码:

class Solution {
    public int findKthLargest(int[] nums, int k) {
        Queue queue = new LinkedList<>();
        Arrays.sort(nums);
        for(int i=nums.length-1;i>=0;i--){
            queue.add(nums[i]);
        }
        for(int i = 1;i<=nums.length;i++){
            if(i==k)
                return queue.poll();
            queue.poll();
        }
        return -1;
    }
}

复杂度分析:

时间复杂度为:O(NlogN)

空间复杂度为:O(1)

方法二:堆

思路:创建一个小顶堆,将所有数组中的元素加入堆中,并保持堆的大小小于等于 k。这样,堆中就保留了前 k 个最大的元素。这样,堆顶的元素就是正确答案。

PS:建一个只能存K个数字的小顶堆,超过K时候,每加进来一个,堆顶就要弹出一个。数组遍历完,最终堆顶的元素就是第K大的(堆里其他元素都比他还要大)

代码:

class Solution {
    public int findKthLargest(int[] nums, int k) {
        // 初始化小根堆
        PriorityQueue heap =
            new PriorityQueue((n1, n2) -> n1 - n2);

        // 保持堆的大小不大于k
        for (int n: nums) {
          heap.add(n);
          if (heap.size() > k)
            heap.poll();
        }

        // 输出队头元素
        return heap.poll();        
  }
}

复杂度分析

  • 时间复杂度 :O(Nlogk)。
  • 空间复杂度 :O(k),用于存储堆元素。

 

你可能感兴趣的:(LeetCode)