【LeetCode每日一题】——2500.删除每行中的最大值

一【题目类别】

  • 优先队列

二【题目难度】

  • 简单

三【题目编号】

  • 2500.删除每行中的最大值

四【题目描述】

  • 给你一个 m x n 大小的矩阵 grid ,由若干正整数组成。
  • 执行下述操作,直到 grid 变为空矩阵:
    • 从每一行删除值最大的元素。如果存在多个这样的值,删除其中任何一个。
    • 将删除元素中的最大值与答案相加。
  • 注意 每执行一次操作,矩阵中列的数据就会减 1
  • 返回执行上述操作后的答案。

五【题目示例】

  • 示例 1:
    在这里插入图片描述

    • 输入:grid = [[1,2,4],[3,3,1]]
    • 输出:8
    • 解释:上图展示在每一步中需要移除的值。
      • 在第一步操作中,从第一行删除 4 ,从第二行删除 3(注意,有两个单元格中的值为 3 ,我们可以删除任一)。在答案上加 4 。
      • 在第二步操作中,从第一行删除 2 ,从第二行删除 3 。在答案上加 3 。
      • 在第三步操作中,从第一行删除 1 ,从第二行删除 1 。在答案上加 1 。
      • 最终,答案 = 4 + 3 + 1 = 8 。
  • 示例 2:
    在这里插入图片描述

    • 输入:grid = [[10]]
    • 输出:10
    • 解释:上图展示在每一步中需要移除的值。
      • 在第一步操作中,从第一行删除 10 。在答案上加 10 。
      • 最终,答案 = 10 。

六【题目提示】

  • m == grid.length
  • n == grid[i].length
  • 1 <= m, n <= 50
  • 1 <= grid[i][j] <= 100

七【解题思路】

  • 其实本题使用排序思路更好想,不过既然本系列的Topic是优先队列,那么就用优先队列解决该问题,不过本质上仍旧是排序的思想
  • 根据题目要求,我们每次要计算每一行的最大值,并将这些最大值再选一个最大值,然后记录该最大值与每一轮得到的最大值求和,最后删除选择的每一行的最大值,然后依次往复这个过程
  • 所以我们为每一行设置一个优先队列,用来记录当前行的值,并且从大到小排序
  • 这样每次我们就可以直接得到当前行的最大值,只需要比较当前列的最大值即可
  • 然后重复上面的过程,就可以得到每一轮的最大值,最后将这些最大值求和后返回即可

八【时间频度】

  • 时间复杂度: O ( m n l o g n ) O(mnlogn) O(mnlogn) m m m n n n分别为传入的二维数组的行数和列数
  • 空间复杂度: O ( m n ) O(mn) O(mn) m m m n n n分别为传入的二维数组的行数和列数

九【代码实现】

  1. Java语言版
class Solution {
    public int deleteGreatestValue(int[][] grid) {
        // 为二维数组的每一行构建优先队列
        int row = grid.length;
        int col = grid[0].length;
        PriorityQueue<Integer>[] pQeueus = new PriorityQueue[row];
        for(int i = 0; i < row; i++) {
            pQeueus[i] = new PriorityQueue<Integer>((a, b) -> b - a);
            for (int num : grid[i]) {
                pQeueus[i].offer(num);
            }
        }
        // 根据优先队列删除每一行的最大值,并求和
        int res = 0;
        for (int j = 0; j < col; j++) {
            int maxNum = 0;
            for (int i = 0; i < row; i++) {
                maxNum = Math.max(maxNum, pQeueus[i].poll());
            }
            res += maxNum;
        }
        // 返回结果
        return res;
    }
}
  1. Python语言版
import heapq

class Solution:
    def deleteGreatestValue(self, grid: List[List[int]]) -> int:
        # 为二维数组的每一行构建优先队列
        row = len(grid)
        col = len(grid[0])
        pQueues = []
        for i in range(0, row):
            row_nums = [-num for num in grid[i]]
            heapq.heapify(row_nums)
            pQueues.append(row_nums)
        
        # 根据优先队列删除每一行的最大值,并求和
        res = 0
        for j in range(0, col):
            max_num = 0
            for i in range(0, row):
                max_num = max(max_num, -heapq.heappop(pQueues[i]))
            res += max_num
        
        # 返回结果
        return res
  1. C++语言版
class Solution {
public:
    int deleteGreatestValue(vector<vector<int>>& grid) {
        // 为二维数组的每一行构建优先队列
        int row = grid.size();
        int col = grid[0].size();
        std::vector<std::priority_queue<int>> pQueues(row);
        for (int i = 0; i < row; i++) {
            for (int num : grid[i]) {
                pQueues[i].push(num);
            }
        }

        // 根据优先队列删除每一行的最大值,并求和
        int res = 0;
        for (int j = 0; j < col; j++) {
            int maxNum = 0;
            for (int i = 0; i < row; i++) {
                maxNum = max(maxNum, pQueues[i].top());
                pQueues[i].pop();
            }
            res += maxNum;
        }
        
        // 返回结果
        return res;
    }
};

十【提交结果】

  1. Java语言版
    在这里插入图片描述

  2. Python语言版
    在这里插入图片描述

  3. C++语言版
    在这里插入图片描述

  • 18
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

IronmanJay

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值