题目地址:
https://www.lintcode.com/problem/kth-largest-in-n-arrays/description
给定 N N N个数组,求所有数的第 k k k大的数。
思路是多路归并。先将每个数组排序从大到小,然后开一个最大堆,将每个数组的最大数加进堆里。接着出堆 k − 1 k-1 k−1次,每次出堆的时候,就把它右边一位的数入堆。出堆 k − 1 k-1 k−1次后的堆顶即为所求。代码如下:
import java.util.Arrays;
import java.util.PriorityQueue;
public class Solution {
class Pair {
int x, y, val;
public Pair(int x, int y, int val) {
this.x = x;
this.y = y;
this.val = val;
}
}
/**
* @param arrays: a list of array
* @param k: An integer
* @return: an integer, K-th largest element in N arrays
*/
public int KthInArrays(int[][] arrays, int k) {
// write your code here
// 开一个最大堆
PriorityQueue<Pair> maxHeap = new PriorityQueue<>((p1, p2) -> -Integer.compare(p1.val, p2.val));
// 也可以排序后不翻转,直接从把每个数组的最后一个数进堆
for (int i = 0; i < arrays.length; i++) {
Arrays.sort(arrays[i]);
if (arrays[i].length > 0) {
maxHeap.offer(new Pair(i, arrays[i].length - 1, arrays[i][arrays[i].length - 1]));
}
}
for (int i = 0; i < k - 1; i++) {
Pair cur = maxHeap.poll();
if (cur.y >= 1) {
maxHeap.offer(new Pair(cur.x, cur.y - 1, arrays[cur.x][cur.y - 1]));
}
}
return maxHeap.peek().val;
}
}
时间复杂度 O ( ∑ i = 1 l n i log n i + k log l ) O(\sum_{i=1}^{l}n_i\log n_i+k\log l) O(∑i=1lnilogni+klogl),空间 O ( l ) O(l) O(l),其中 l l l是数组的个数, n i n_i ni是第 i i i个数组的长度。