[Leetcode]Valid Sudoku

Determine if a Sudoku is valid, according to: Sudoku Puzzles - The Rules.

The Sudoku board could be partially filled, where empty cells are filled with the character '.'.


A partially filled sudoku which is valid.

Note:
A valid Sudoku board (partially filled) is not necessarily solvable. Only the filled cells need to be validated.

這是一道用到hash map的題目。

拿到這道題一上來的思路就是遍歷所有元素,將每個元素都和同行、同列、同九宮格的元素比較,然後發現有很多重複操作。

然後想到可以用hash map(思路來源於Single Number II),將每行、每列、每九宮格出現的元素全部作爲key存放在一個map中,如果當前行、列、方九宮格再次出現同一元素,則證明數獨非法。

第一遍ac的代碼(遍歷三遍數組,分別確定行、列、九宮格是否合法)

class Solution {
public:
	bool isValidSudoku(vector<vector<char> > &board) {
		int n = board.size();
		if(!rowValid(board, n)) return false;
		if(!colValid(board, n)) return false;
		if(!blockValid(board,n)) return false;
		return true;
	}
	bool rowValid(vector<vector<char> > board,int n){
		map<char, int> m;
		for (int i = 0; i < n; i++){
			for (int j = 0; j < n; j++){
				if (board[i][j] == '.') continue;
				if (m.find(board[i][j]) == m.end())
					m[board[i][j]] = 1;
				else return false;
			}
			m.clear();
		}
		return true;
	}
	bool colValid(vector<vector<char> > board, int n){
		map<char, int> m;
		for (int i = 0; i < n; i++){
			for (int j = 0; j < n; j++){
				if (board[j][i] == '.') continue;
				if (m.find(board[j][i]) == m.end())
					m[board[j][i]] = 1;
				else return false;
			}
			m.clear();
		}
		return true;
	}
	bool blockValid(vector<vector<char> > board, int n){
		int m = n / 3;
		map<char, int> mp;
		for (int i = 0; i < m; i++){
			for (int j = 0; j < m; j++){
				for (int p = 0; p < 3; p++){
					for (int q = 0; q < 3; q++){
						if (board[i*3+p][j*3+q] == '.') continue;
						if (mp.find(board[i*3+p][j*3+q]) == mp.end()){
							mp[board[i * 3 + p][j * 3 + q]] = 1;
						}
						else return false;
					}
				}
				mp.clear();
			}
		}
		return true;
	}
};
isValidSudoku裏邊本來寫的 return rowValid(board,n)&&colValid(board,n)&&blockValid(board,n),後來發現這樣寫可能拉高了平均複雜度,最後還是分開寫了。

第二遍ac的代碼(只遍歷一遍數組,用三個二維數組分別存放行、列、九宮格中元素出現的情況):

class Solution{
public:
	bool isValidSudoku(vector<vector<char> > &board){
		vector<vector<bool> > rows(9, vector<bool>(9, false));
		vector<vector<bool> > cols(9, vector<bool>(9, false));
		vector<vector<bool> > blocks(9, vector<bool>(9, false));

		for (int i = 0; i < 9; i++){
			for (int j = 0; j < 9; j++){
				if (board[i][j] == '.') continue;
				int num = board[i][j] - '1';
				if (rows[i][num] || cols[j][num] || blocks[i - i % 3 + j / 3][num])
					return false;
				rows[i][num] = cols[j][num] = blocks[i - i % 3 + j / 3][num] = true;
			}
		}
		return true;
	}
};

這段代碼比較簡潔一點,九宮格的座標換算可能比較難想。前後兩個方法的效率差距還挺大的。第一個120ms AC,第二個96ms AC。個人感覺是不是map的find方法浪費了時間?


發佈了35 篇原創文章 · 獲贊 1 · 訪問量 1萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章