js判断一个数独的解是否合法

偷了个懒,把解释都放到注释里面了。

js 代码:

	var n = 9; // 这个表示数独的规模

    
	function getArr(){
		return [0,0,0,0,0,0,0,0,0,0];
	}
	
	function checkRowAndRol(board) {
		for (var i = 0; i < n; i++) {
			var arr = getArr();
			for (var j = 0; j < n; j++) {
			    if(arr[board[i][j]] != 0)
			    	return false;
			    arr[board[i][j]] = 1;
			}

			var arr = getArr();
			for (var j = 0; j < n; j++) {
			    if(arr[board[j][i]] != 0)
			    	return false;
			    arr[board[j][i]] = 1;
			}
		}
		return true;
	}

	function doneOrNot(board) {
		if(!checkRowAndRol(board)) return "try again!";

		for( var i = 0; i < n; i++){
			for( var j = 0; j < n; j++){
				if(!checkNine(board , i , j)) return "try again!";
			}
		}
		return "Finished!";
	}
	function checkNine(board , heigth , weidth){
		h = Math.floor(weidth / 3);
		w = Math.floor(heigth / 3);

        //除以3,计算出当前位置处于第几个九宫格
        //乘以3,计算出当前九宫格开始的位置
        //加3,得到当前九宫格终止位置

		for(var i = w * 3; i < w * 3 + 3; i++){
			for(var j = h * 3; j < h * 3 + 3; j++){
			    if(i == heigth && j == weidth) continue;
			    if(board[i][j] == board[heigth][weidth]) return false;
			}
		}
		return true;
	}

今天在codewars 上刷题,看到了判断数独解法是否正确的题,于是尝试了一种新写法:

Java 代码

public class SudokuValidator {
    public static boolean check(int[][] sudoku) {
        int [][] flag = new int[3][3];
        for(int i = 0 ; i < sudoku.length ; i++){
            int flag1 = 0,flag2 = 0;

            for(int j = 0;j<sudoku[i].length;j++){
                flag1 ^= (1 << sudoku[i][j]);
                flag2 ^= (1 << sudoku[j][i]);
                flag[i/3][j/3] ^= (1 << sudoku[i][j]);
            }
            if (flag1 != 0x3FE || flag2 != 0x3FE) return false;
        }

        for(int i = 0; i < 3;i++)
            for(int j = 0; j< 3;j++)
                if (flag[i][j] != 0x3FE) return false;
        return true;
    }
}

效率比之前的代码高出不少。

 解释下思路:

1.数独要满足三种情况中不能有重复的数字,这些数字是 1 到 9 之间的整数。

2.每一种情况一共有九个计算项(九行,九列,九个九宫格)。

3.每个计算项用一个变量保存是否有重复。

4.利用异或运算的性质( 1 ^ 1 == 0 , 1 ^ 0 == 1 )来判断是否重复。

5.行和列复用了同两个变量来计算。

6.九宫格没有想到复用变量的方法,于是开了一个二维数组:

    利用 i / 3 , j / 3 来计算当前元素是属于哪一个九宫格的,然后计算对应位置的值

7.最后判断 每一个计算项的计算结果是不是 1111111110(二进制) 也就是 0xFE ,如果不是,那对应情况的对应项一定有重复的数字。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值