↓快轉到主要內容
  1. LeetCode/

LeetCode 36: Valid Sudoku

·1 分鐘· ·
LeetCode Medium Array Hash-Table Matrix
Wei Yi Chung
作者
Wei Yi Chung
Working at the contributing of open source, distributed systems, and data engineering.
目錄

基本資料
#

難易度: medium 第一次嘗試:2022-10-21

  • 提交紀錄:Runtime Error ×5 → Accepted → Wrong Answer ×3 → Accepted → Runtime Error ×3 → Accepted ×3

解題思路
#

只檢查已經填的格子,不用判斷有沒有解。每個數字產生三個 key:(d, 'r', i)、(d, 'c', j)、(d, 'b', i // 3, j // 3),任何一個重複出現就不合法(Hash Table)。宮格的編號是 (i // 3, j // 3)。

我的嘗試
#

這題 2022-10 和 2022-11 寫了兩次,錯了 11 次:

  • 一開始寫成檢查列、欄、宮格三個 helper,幾次 RE 之後 AC。
  • 接著想改成「把 key 放進同一個集合」的寫法,但只放了列和欄,忘了 3 × 3 宮格:同一個宮格裡兩個相同的數字(不同列也不同欄)沒被抓到,回傳 True。
  • 2022-11 重寫時加上 (數字, (i // 3, j // 3)) 這個 key 才 AC。

正確解法
#

class Solution:
    def isValidSudoku(self, board: List[List[str]]) -> bool:
        seen = set()
        for i in range(9):
            for j in range(9):
                d = board[i][j]
                if d == ".":
                    continue
                for key in ((d, "r", i), (d, "c", j), (d, "b", i // 3, j // 3)):
                    if key in seen:
                        return False
                    seen.add(key)
        return True

複雜度
#

時間 O(81),空間 O(81)。

要特別避免的錯誤
#

  • 3 × 3 宮格也要檢查。
  • 列和欄的 key 要能區分,(d, i) 和 (i, d) 這種位置互換的寫法可以,但加上標籤比較清楚。

面試口說整理
#

每個已填的數字在列、欄和三乘三的宮格各只能出現一次,我把數字和它所在的列、欄、宮格編號組成三個 key 放進同一個集合,重複就不合法。宮格編號是 i // 3、j // 3。

相關文章

LeetCode 31: Next Permutation
·1 分鐘
LeetCode Medium Array Two-Pointers
LeetCode 31 解題筆記:從右邊找第一個下降的位置 i,跟右邊比它大的最小值交換,再把 i 之後反轉;比較時要包含等於
LeetCode 33: Search in Rotated Sorted Array
·1 分鐘
LeetCode Medium Array Binary-Search
LeetCode 33 解題筆記:旋轉後 mid 的左右一定有一邊是排序好的,判斷目標在不在那一邊,在就往那邊找,不在就去另一邊
LeetCode 34: Find First and Last Position of Element in Sorted Array
·1 分鐘
LeetCode Medium Array Binary-Search
LeetCode 34 解題筆記:做兩次 lower bound:第一個 >= target 的位置,以及第一個 >= target + 1 的位置減一
LeetCode 39: Combination Sum
·1 分鐘
LeetCode Medium Array Backtracking
LeetCode 39 解題筆記:同一個數可以重複選,所以遞迴時下一層從 i 開始(不是 i + 1),這樣也避免了順序不同的重複
LeetCode 40: Combination Sum II
·1 分鐘
LeetCode Medium Array Backtracking
LeetCode 40 解題筆記:每個數只能用一次而且有重複,排序後下一層從 i + 1 開始,同一層跳過跟前一個相同的值
LeetCode 46: Permutations
·1 分鐘
LeetCode Medium Array Backtracking
LeetCode 46 解題筆記:每一層從還沒用過的數裡選一個,用 used 陣列標記,path 滿了就記錄