51. N-Queens(N皇后)

题目链接:https://leetcode.com/problems/n-queens/

思路:回溯法,如果你会写八皇后问题,那么这道题就很简单了。

AC 5ms Java:

具体思路注释在程序中了。

class Solution {
    List<List<String>> ans=new ArrayList();
    public List<List<String>> solveNQueens(int n) {
        String[][] strs=new String[n][n];
        for(int i=0;i<n;i++)
            for(int j=0;j<n;j++)
                strs[i][j]=".";//初始化二维数组
        backtrace(0,n,strs);
        return ans;
    }
    public void backtrace(int row,int n,String[][] strs){
        if(row>n-1){//当行数大于N-1时,说明已经找到了一组解。
            List<String> list=new ArrayList();
            for(int i=0;i<n;i++){
                StringBuilder sb=new StringBuilder();
                for(int j=0;j<n;j++){
                    sb.append(strs[i][j]);
                }
                list.add(sb.toString());
            }
            ans.add(list);
        }
        for(int col=0;col<n;col++){
            if(check(strs,row,col)){//检查通过时,继续递归下一行
                strs[row][col]="Q";
                backtrace(row+1,n,strs);
                strs[row][col]=".";//注意别忘了再更新回来。
            }
        }
    }
    public boolean check(String[][] strs,int row,int col){
        int n=strs.length;
        for(int t=0;t<n;t++){//检查列冲突
            if(strs[t][col].equals("Q"))
                return false;
        }
        for(int t=0;t<n;t++){//检查行冲突
            if(strs[row][t].equals("Q"))
                return false;
        }
        for(int i=row-1,j=col-1;i>=0&&j>=0;i--,j--){
            if(strs[i][j].equals("Q"))//检查左上对角线冲突
                return false;
        }
        for(int i=row-1,j=col+1;i>=0&&j<n;i--,j++){
            if(strs[i][j].equals("Q"))//检查右上对角线冲突
                return false;
        }
        return true;
    }
}

我的程序有两个地方还可以优化,一个是二维数组初始化哪里,

另一个就是当此数组满足条件时添加结果到ans里。

*********************************************************************************************************************************************************************************************************二更的华丽分界线*****************************************************************************

后来发现用char数组代替String数组在速度上要快不少。

AC 3ms beats 96% Java:

class Solution {
    List<List<String>> ans=new ArrayList();
    public List<List<String>> solveNQueens(int n) {
        char[][] chars=new char[n][n];
        for(int i=0;i<n;i++)
            for(int j=0;j<n;j++)
                chars[i][j]='.';//初始化二维数组
        backtrace(0,n,chars);
        return ans;
    }
    public void backtrace(int row,int n,char[][] chars){
        if(row>n-1){//当行数大于N-1时,说明已经找到了一组解。
            List<String> list=new ArrayList();
            for(int i=0;i<n;i++){
                StringBuilder sb=new StringBuilder();
                for(int j=0;j<n;j++){
                    sb.append(String.valueOf(chars[i][j]));
                }
                list.add(sb.toString());
            }
            ans.add(list);
            return;
        }
        for(int col=0;col<n;col++){
            if(check(chars,row,col)){//检查通过时,继续递归下一行
                chars[row][col]='Q';
                backtrace(row+1,n,chars);
                chars[row][col]='.';//注意别忘了再更新回来。
            }
        }
    }
    public boolean check(char[][] chars,int row,int col){
        int n=chars.length;
        for(int t=0;t<n;t++){//检查列冲突
            if(chars[t][col]=='Q')
                return false;
        }
        for(int t=0;t<n;t++){//检查行冲突
            if(chars[row][t]=='Q')
                return false;
        }
        for(int i=row-1,j=col-1;i>=0&&j>=0;i--,j--){
            if(chars[i][j]=='Q')//检查左上对角线冲突
                return false;
        }
        for(int i=row-1,j=col+1;i>=0&&j<n;i--,j++){
            if(chars[i][j]=='Q')//检查右上对角线冲突
                return false;
        }
        return true;
    }
}

猜你喜欢

转载自blog.csdn.net/God_Mood/article/details/88016064
今日推荐