LeetCodeDay36 —— 矩陣置零★★☆

73. 矩陣置零

描述
  • 給定一個(gè) m x n 的矩陣,如果一個(gè)元素為 0,則將其所在行和列的所有元素都設(shè)為 0。請使用原地算法。
示例
示例 1:
  輸入:
    [
      [1,1,1],
      [1,0,1],
      [1,1,1]
    ]
  輸出:
    [
      [1,0,1],
      [0,0,0],
      [1,0,1]
    ]
示例 2:
  輸入:
    [
      [0,1,2,0],
      [3,4,5,2],
      [1,3,1,5]
    ]
  輸出:
    [
      [0,0,0,0],
      [0,4,5,0],
      [0,3,1,0]
    ]
進(jìn)階:
  一個(gè)直接的解決方案是使用  O(mn) 的額外空間,但這并不是一個(gè)好的解決方案。
  一個(gè)簡單的改進(jìn)方案是使用 O(m + n) 的額外空間,但這仍然不是最好的解決方案。
  你能想出一個(gè)常數(shù)空間的解決方案嗎?
思路
  1. 時(shí)間復(fù)雜度O(mn),空間復(fù)雜度O(mn)的算法,復(fù)制一份Matrix,將0對應(yīng)行列的元素置位0.
  2. 時(shí)間復(fù)雜度O(mn),空間復(fù)雜度O(m + n)的算法,利用一個(gè)M大小和一個(gè)N大小的數(shù)組,保存0元素的小標(biāo),然后將對應(yīng)行列的元素置位0.
  3. 時(shí)間復(fù)雜度O(mn),空間復(fù)雜度O(1)的算法,利用首行首列的元素來表示該行該列是否有0元素,然后將對應(yīng)行列的元素置位0.該方法需先統(tǒng)計(jì)首行首列自己是否有0元素,最后將首行首列置0.(參考)
Tips
  1. 題目需要遍歷每個(gè)元素,所以時(shí)間復(fù)雜度O(mn)是較難優(yōu)化的,突破點(diǎn)在于空間復(fù)雜度。
  2. 第一種解法直接復(fù)制了整個(gè)數(shù)組,仔細(xì)思考下其實(shí)只需保存0元素的小標(biāo)即可,此時(shí)可將空間復(fù)雜度優(yōu)化為O(m + n)
  3. 進(jìn)一步優(yōu)化,要將空間復(fù)雜度降為O(1),則需利用數(shù)組本身來保存0的位置了。不難想到可以將上述額外的兩個(gè)數(shù)組轉(zhuǎn)換為首行首列,具體步驟如下:
    1)檢查并記錄第一行和第一列是否需要?dú)w零;
    2)遍歷矩陣,一旦發(fā)現(xiàn)某個(gè)元素為0,則將它所在的行和列的第一個(gè)元素置為0;
    3)遍歷第一行和第一列,如果是0,則將其對應(yīng)的整個(gè)行或者整個(gè)列的元素置為0;
    4)如果第一行或者第一列需要?dú)w零,則將其歸零。時(shí)間復(fù)雜度為O(m*n),空間復(fù)雜度為O(1)。
class Solution_73_01 {
 public:
  void setZeroes(vector<vector<int>>& matrix) {
    vector<vector<int>> tmp = matrix;
    for (int i = 0; i < matrix.size(); ++i) {
      for (int j = 0; j < matrix[i].size(); ++j) {
        if (tmp[i][j] == 0) {
          for (int k = 0; k != matrix[i].size(); ++k) matrix[i][k] = 0;
          for (int k = 0; k != matrix.size(); ++k) matrix[k][j] = 0;
        }
      }
    }
  }
};

class Solution_73_02 {
 public:
  void setZeroes(vector<vector<int>>& matrix) {
    if (matrix.empty()) return;
    int hight = matrix.size(), width = matrix[0].size();
    vector<bool> row0, col0;
    row0.assign(hight, false);
    col0.assign(width, false);
    for (int i = 0; i < hight; ++i) {  //記錄0點(diǎn)的位置
      for (int j = 0; j < width; ++j) {
        if (matrix[i][j] == 0) {
          row0[i] = true;
          col0[j] = true;
        }
      }
    }
    for (int i = 0; i < row0.size(); ++i) {
      if (!row0[i]) continue;
      for (int j = 0; j < width; ++j) {
        matrix[i][j] = 0;
      }
    }
    for (int i = 0; i < col0.size(); ++i) {
      if (!col0[i]) continue;
      for (int j = 0; j < hight; ++j) {
        matrix[j][i] = 0;
      }
    }
  }
};

class Solution_73_03 {
 public:
  void setZeroes(vector<vector<int>>& matrix) {
    if (matrix.empty()) return;
    int hight = matrix.size(), width = matrix[0].size();
    bool isHasZeroRow = false, isHasZeroCol = false;
    for (int i = 0; i < hight; ++i) {
      if (matrix[i][0] == 0) {
        isHasZeroRow = true;
        break;
      }
    }
    for (int i = 0; i < width; ++i) {
      if (matrix[0][i] == 0) {
        isHasZeroCol = true;
        break;
      }
    }
    // 將0元素所在行列的第一個(gè)元素置為0
    for(int i = 1; i < hight; ++i){
      for(int j = 1; j < width; ++j){
        if(matrix[i][j] == 0){
          matrix[i][0] = 0;
          matrix[0][j] = 0;
        }
      }
    }

    // 根據(jù)首行、首列將對應(yīng)元素置0
    for(int row = 1; row < hight; ++row){
      if(matrix[row][0] == 0){
        for(int col = 1; col < width; ++col){
          matrix[row][col] = 0;
        }
      }
    }
    for(int col = 1; col < width; ++col){
      if(matrix[0][col] == 0){
        for(int row = 1; row < hight; ++row){
          matrix[row][col] = 0;
        }
      }
    }

    cout<< isHasZeroRow << " " << isHasZeroCol << endl;
    // 處理首行、首列
    if(isHasZeroRow){
      for(int i = 0; i < hight; ++i){
        matrix[i][0] = 0;
      }
    }
    if(isHasZeroCol){
      for(int i = 0; i < width; ++i){
        matrix[0][i] = 0;
      }
    }
  }
};
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 給定一個(gè) m x n 的矩陣,如果一個(gè)元素為 0,則將其所在行和列的所有元素都設(shè)為 0。請使用原地算法。 進(jìn)階: ...
    susu2016閱讀 2,391評論 0 2
  • 9.3.3 快速排序 ??快速排序?qū)⒃瓟?shù)組劃分為兩個(gè)子數(shù)組,第一個(gè)子數(shù)組中元素小于等于某個(gè)邊界值,第二個(gè)子數(shù)組中的...
    RichardJieChen閱讀 1,949評論 0 3
  • Spring Cloud為開發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見模式的工具(例如配置管理,服務(wù)發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,506評論 19 139
  • 10月13日,晚,微信聊天,對面,是自己的好朋友,只是,聊到最后,卻未如以往開開心心結(jié)束,看著床邊的書,沒有...
    依戀三國情閱讀 324評論 0 1
  • 分割線滿屏 隱藏某一個(gè)cell分割線 [cell setSeparatorInset:UIEdgeInsetsMa...
    vision_colion閱讀 449評論 0 3

友情鏈接更多精彩內(nèi)容