码迷,mamicode.com
首页 > 其他好文 > 详细

LeetCode-52 N-Queens II

时间:2015-02-12 13:52:49      阅读:175      评论:0      收藏:0      [点我收藏+]

标签:

Follow up for N-Queens problem.

Now, instead outputting board configurations, return the total number of distinct solutions.

技术分享

 

首先需要确定什么位置放置皇后是合法的(满足同一行,同一列,同一对角线上不存在两个皇后,即为一种可行解),设两个皇后的位置为(x1,y1),(x2,y2),

限制条件为:x1 != x2(同一行不存在两个皇后)

      y1 != y2(同一列不存在两个皇后)

      x1 + y1 != x2 + y2(45度对角线上不存在两个皇后)

      x1 - y1 != x2 - y2(135度对角线上不存在两个皇后)

public boolean valid(int h, int l) {
        //check column
        if(cols.contains(l))
            return false;
        //check diagonal(45)
        if(diagonals1.contains(h+l))
            return false;
        //check diagonal(135)
        if(diagonals2.contains(h-l))
            return false;
        return true;
    }

使用回溯法分别给出递归和非递归的代码。

 递归代码:

/***********************************************
     * i         第i个皇后(即第i行)
     * total    表示n皇后问题解的个数
     * n         皇后个数
     ***********************************************/
    public void totalNQueensRecursion(int i, int n) {
        for(int j=0; j<n; j++) {
            if(valid(i, j)) {
                if(i != n-1) {
                    cols.add(j);
                    diagonals1.add(i+j);
                    diagonals2.add(i-j);
                    totalNQueensRecursion(i+1, n);
                    cols.remove(j);
                    diagonals1.remove(i+j);
                    diagonals2.remove(i-j);
                } else {
                    total++;
                }
            }
        }
    }

 

非递归代码:

public int totalNQueens(int n) {
        int j = 0;
        for(int i=0; i<n; i++) {
            for(; j<n; j++) {
                if(valid(i, j)) {
                    if(i != n-1) {
                        cols.add(j);
                        diagonals1.add(i+j);
                        diagonals2.add(i-j);
                        j = 0;
                        break;
                    } else {
                        total++;
                        continue;
                    }
                } 
            }
            
            //turn back
            if(j >= n) {
                for(i=i-1; i>=0; i--) {
                    if(cols.get(i) < n-1) {
                        j = cols.get(i) + 1;
                        cols.remove(i);
                        diagonals1.remove(i);
                        diagonals2.remove(i);
                        break;
                    } else {
                        cols.remove(i);
                        diagonals1.remove(i);
                        diagonals2.remove(i);
                    }
                    
                }
                if(i < 0) {
                    return total;
                }
                i--;//抵消for循环中的i++;
            }
        }
        return total;
    }

 

在上述两段代码中,都使用的集合:

private List<Integer> cols = new ArrayList<Integer>();
private List<Integer> diagonals1 = new ArrayList<Integer>();//45度对角线,和相同
private List<Integer> diagonals2 = new ArrayList<Integer>();//135度对角线,差相同

 

LeetCode-52 N-Queens II

标签:

原文地址:http://www.cnblogs.com/linxiong/p/4287756.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!