题解 | #两个有序数组间相加和的Topk问题#

两个有序数组间相加和的Topk问题

https://www.nowcoder.com/practice/7201cacf73e7495aa5f88b223bbbf6d1

import java.util.*;

// 注意类名必须为 Main, 不要有任何 package xxx 信息
public class Main {
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int n = in.nextInt(), k = in.nextInt();
        int[] arr1 = new int[n], arr2 = new int[n];
        for (int i = 0; i < n; i++) arr1[i] = in.nextInt();
        for (int i = 0; i < n; i++) arr2[i] = in.nextInt();
        int[] topK = topKsum(arr1, arr2, Math.min(k, 2 * n));
        for (int x : topK) System.out.print(x + " ");
        System.out.println();
        in.close();
    }
    private static int[] topKsum(int[] arr1, int[] arr2, int k) {
        int[] ans = new int[k];
	    // 创建一个大根堆,每次存储arr1[i] + arr2[j] 的位置和值,每次从堆顶取数
        Queue<Node> maxHeap = new PriorityQueue<>((o1, o2) -> o2.sum - o1.sum);
	  	// 用于去重
        Set<String> visited = new HashSet<>();
        int i = arr1.length - 1, j = arr2.length - 1, idx = 0;
        maxHeap.offer(new Node(i, j, arr1[i] + arr2[j]));
        visited.add(pos(i, j));
        while (idx < k) {
            Node cur = maxHeap.poll();
            ans[idx++] = cur.sum;
            i = cur.i;
            j = cur.j;
            if (i - 1 >= 0 && !visited.contains(pos(i - 1, j))) {
                maxHeap.add(new Node(i - 1, j, arr1[i - 1] + arr2[j]));
                visited.add(pos(i - 1, j));
            }
            if (j - 1 >= 0 && !visited.contains(pos(i, j - 1))) {
                maxHeap.add(new Node(i, j - 1, arr1[i] + arr2[j - 1]));
                visited.add(pos(i, j - 1));
            }
        }
        return ans;
    }
    private static class Node {
        private int i;   // arr1中的位置
        private int j;   // arr2中的位置
        private int sum; // arr[i] + arr[j]的值
        public Node (int i, int j, int sum) {
            this.i = i;
            this.j = j;
            this.sum = sum;
        }
    }
    private static String pos(int i, int j) {
        return String.format("%d_%d", i, j);
    }
}

#优先队列的应用##topK问题##大根堆#
线性表基础 文章被收录于专栏

链表、递归、栈

全部评论

相关推荐

点赞 收藏 评论
分享
牛客网
牛客企业服务