力扣215.数组中的第K个最大元素

Posted 一个拿着底层薪资操着架构师的心的码农

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了力扣215.数组中的第K个最大元素相关的知识,希望对你有一定的参考价值。

215. 数组中的第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 ≤ 数组的长度。

思路一:排序后取值

复杂度分析:

时间复杂度:排序时间为O(nlogn),所以时间为O(nlogn)

空间复杂度:O(1)

思路二:利用堆

维持一个大小为K的最小堆,堆顶的元素始终是当前所有元素中第K大的元素

 1 class Solution {
 2     public int findKthLargest(int[] nums, int k) {
 3         PriorityQueue<Integer> heap = new PriorityQueue<>();    // 最小堆
 4         for(int i : nums){
 5             heap.offer(i);
 6             if(heap.size() > k){
 7                 heap.poll();        // 维持堆的大小为k
 8             }
 9         }
10         return heap.poll();
11     }
12 }

力扣测试时间为:6ms, 空间为40.2MB

复杂度分析:

时间复杂度:一个维持堆大小为k的过程,所以时间复杂度为O(Nlogk)

空间复杂度:O(k),也就是堆的大小

思路三:

借助快排的过程

 1 class Solution {
 2     public int findKthLargest(int[] nums, int k) {
 3         // 借助快排的过程
 4         return quickSort(nums, 0, nums.length - 1, nums.length - k);
 5     }
 6 
 7     public int partition(int[] nums, int left, int right){
 8         // 选取第一个元素为主元
 9         int pivot = nums[left];
10         
11         while(left < right){
12             while(left < right && nums[right] >= pivot){
13                 right--;
14             }
15             nums[left] = nums[right];
16 
17             while(left < right && nums[left] <= pivot){
18                 left++;
19             }
20             nums[right] = nums[left];
21         }
22         nums[left] = pivot;
23         return left;
24     }
25 
26     public int quickSort(int[] nums, int left, int right, int k){
27         // 如果经过一轮快排分区后主元位置刚好是k,那么可以直接退出了
28         int mid = partition(nums, left, right);
29         if(mid == k){
30             return nums[k];
31         }else if(mid > k){
32             return quickSort(nums, left, mid - 1, k);
33         }else{
34             return quickSort(nums, mid + 1, right, k);
35         }
36     }
37 }

力扣测试时间为9ms, 空间为40.6MB

复杂度分析:

时间复杂度:每次将数组分成两段,只会选择其中一段进行partition操作,所以时间复杂度为O(N+N/2 + N/4 + 1) =,所以时间复杂度为O(N)

空间复杂度为:O(1)

 思路参考:

https://leetcode-cn.com/problems/kth-largest-element-in-an-array/solution/shu-zu-zhong-de-di-kge-zui-da-yuan-su-by-leetcode/

 

以上是关于力扣215.数组中的第K个最大元素的主要内容,如果未能解决你的问题,请参考以下文章

215. 数组中的第K个最大元素

LeetCode 215. 数组中的第K个最大元素 | Python

215. 数组中的第K个最大元素

[LeetCode]215. 数组中的第K个最大元素(堆)

leetcode 215. 数组中的第K个最大元素(快速排序)

215. 数组中的第K个最大元素