LeetCode 73. 矩阵置零(C++)*

该博客讨论了一种在给定矩阵中遇到0元素时,如何使用原地算法将对应行和列元素全部置0的策略。具体方法是利用矩阵的第一行和第一列作为标记,记录其他元素的0位置。首先检查第一行和第一列是否有0,然后遍历矩阵,用第一行和第一列标记0元素。最后,根据第一行和第一列的标记来实际设置矩阵的0元素,包括处理第一行和第一列的情况。这种方法避免了额外的空间使用,仅用常量空间即可实现。
摘要由CSDN通过智能技术生成

思路:
1.用额外的额数组或者哈希表来记录矩阵元素为0的位置
2.在原地实现记录,那就要用本来矩阵的空间作为记录数组。我们选用第一行和第一列来记录其他行列的元素情况。因为如果一个元素为0,则它所在行列都置为0,所以我们只需要记录一个元素的第一行和第一列标记,就可以实现:
(比如位置[i][j],只需要将[i][0]和[0][j]置0标记,这样对于第i行和第j列的元素,只要通过该元素的第0行和第0列的标记就可以判断是否应该置0)。
我们先通过行列标记将其余行列元素置0,最后根据是否第一行列有0元素来将第一行列元素置0,这样不会影响到其他元素的置0判断条件。
原题链接:https://leetcode.cn/problems/set-matrix-zeroes/description/?favorite=2ckc81c

1.题目如下:

给定一个 m x n 的矩阵,如果一个元素为 0 ,则将其所在行和列的所有元素都设为 0 。请使用 原地 算法。

示例 1:

输入:matrix = [[1,1,1],[1,0,1],[1,1,1]]
输出:[[1,0,1],[0,0,0],[1,0,1]]

示例 2:

输入:matrix = [[0,1,2,0],[3,4,5,2],[1,3,1,5]]
输出:[[0,0,0,0],[0,4,5,0],[0,3,1,0]]

提示:

m == matrix.length
n == matrix[0].length
1 <= m, n <= 200
-231 <= matrix[i][j] <= 231 - 1

进阶:

一个直观的解决方案是使用 O(mn) 的额外空间,但这并不是一个好的解决方案。 一个简单的改进方案是使用 O(m + n)
的额外空间,但这仍然不是最好的解决方案。 你能想出一个仅使用常量空间的解决方案吗?

2.代码如下:

class Solution {

public:
//思路一:使用集合来存储元素0所在的行列坐标,需要额外空间

//思路二:使用mark矩阵来标记0元素

//思路三:要在原地实现 用矩阵的自带空间实现记录
/*
    首先用变量记录第一行和第一列是否有0元素;
    再用第一行和第一列的数组来记录其他行列是否有0元素
*/
    void setZeroes(vector<vector<int>>& matrix) {
        int m=matrix.size();
        int n=matrix[0].size();
        //变量记录第一行和第一列的情况,这里是为最后对第一行和第一列置0
        int flag_col0=false,flag_row0=false;
        for (int i=0;i<m;i++) {
            if (!matrix[i][0]) {
                flag_col0=true;
            }
        }
        for (int j=0;j<n;j++) {
            if (!matrix[0][j]) {
                flag_row0=true;
            }
        }
        for (int i=1;i<m;i++) {
            for (int j=1;j<n;j++) {
                if (!matrix[i][j]) {
                    // 用第一列和第一行作为记录数值,通过矩阵的性质来定位为0的元素位置
                    matrix[i][0]=matrix[0][j] = 0;
                }
            }
        }

        //通过第一行和第一列的标记,只要该位置所在的第一行or第一列标记是0的,就将元素置为0
        for (int i=1;i<m;i++) {
            for (int j=1;j<n;j++) {
                if (!matrix[i][0] || !matrix[0][j]) {
                    matrix[i][j]=0;
                }
            }
        }
        // 对第一行和第一列处理,如果第一列or第一行有0元素,则第一行or第一列全置为0,
        // 最后对第一列第一行处理不会影响到其他列的情况,同时原本第一列和第一行为0的标记也会作为其他位置元素置0的条件
        if(flag_col0) {
            for (int i=0;i<m;i++) {
                matrix[i][0]=0;
            }
        }
        if(flag_row0) {
            for (int j=0;j<n;j++) {
                matrix[0][j]=0;
            }
        }
    }

};
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

_panbk_

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

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

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

打赏作者

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

抵扣说明:

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

余额充值