利用二重循环的下标来表示行、列和小正方形,减少不必要的数据存储,每一次内循环都代表着对一行或是一列或是一个小正方形的遍历。外循环则代表对下一行,下一列和下一个小正方形的遍历。
判断一个 9x9 的数独是否有效。只需要根据以下规则,验证已经填入的数字是否有效即可。
- 数字
1-9
在每一行只能出现一次。 - 数字
1-9
在每一列只能出现一次。 - 数字
1-9
在每一个以粗实线分隔的3x3
宫内只能出现一次。
上图是一个部分填充的有效的数独。
数独部分空格内已填入了数字,空白格用 '.'
表示。
输入:
[
["5","3",".",".","7",".",".",".","."],
["6",".",".","1","9","5",".",".","."],
[".","9","8",".",".",".",".","6","."],
["8",".",".",".","6",".",".",".","3"],
["4",".",".","8",".","3",".",".","1"],
["7",".",".",".","2",".",".",".","6"],
[".","6",".",".",".",".","2","8","."],
[".",".",".","4","1","9",".",".","5"],
[".",".",".",".","8",".",".","7","9"]
]
输出: true
代码:注意字典的键值对
class Solution:
def isValidSudoku(self, board):
"""
:type board: List[List[str]]
:rtype: bool
"""
row = [{},{},{},{},{},{},{},{},{}] # 值:1
col = [{},{},{},{},{},{},{},{},{}]
cell = [{},{},{},{},{},{},{},{},{}]
n = len(board)
for i in range(n):
for j in range(n):
block = 3*(i//3)+j//3 # 找单元
num = board[i][j]
if num != '.':
if num not in row[i] and num not in col[j] and num not in cell[block]:
row[i][num] = 1
col[j][num] = 1
cell[block][num] = 1
else:
return False
# print(row)
# [{'5': 1, '3': 1, '7': 1}, {'6': 1, '1': 1, '9': 1, '5': 1},
# {'9': 1, '8': 1, '6': 1}, {'8': 1, '6': 1, '3': 1},
# {'4': 1, '8': 1, '3': 1, '1': 1}, {'7': 1, '2': 1, '6': 1},
# {'6': 1, '2': 1, '8': 1}, {'4': 1, '1': 1, '9': 1, '5': 1},
# {'8': 1, '7': 1, '9': 1}]
return True
参考:
leetcode 36 Vaild Soduku(有效的数独) python3 最简代码(单次循环)