Day 13 递归 迷宫回溯 八皇后问题

感觉递归还是不太会用就又看了一遍

迷宫回溯

package MiGong;

public class migong {
    public static void main(String[] args) {
        //创建迷宫地图
        int [][]map = new int[10][10];
        for (int i=0;i<map.length;i++){
            map[i][0] = 1;
            map[i][map.length-1] = 1;
            map[0][i] = 1;
            map[map.length-1][i] = 1;
        }
        for (int i = 1; i < 5; i++) {
            map[3][i] = 1;
        }
//        for (int i = 4; i < 9; i++) {
//            map[6][i] = 1;
//        }
        for (int i = 0; i < map.length; i++) {
            for (int j = 0; j < map[i].length; j++) {
                System.out.print(map[i][j]+"\t");
            }
            System.out.println();
        }
        //调用寻路
        FindWay(map,1,1);
        System.out.println("寻路后");
        for (int i = 0; i < map.length; i++) {
            for (int j = 0; j < map[i].length; j++) {
                System.out.print(map[i][j]+"\t");
            }
            System.out.println();
        }

    }
    //迷宫回溯问题
    //
    /**
     * 运行原理就是 传入当前位置 然后向下走 然后以下一格位置为原点 再向下走
     * 如果当前原点位置向下走不通 那么向右走 然后以右一格为原点如果右也走不通那么向上 再走不通向左 如果左也走不通 即当前路是死路
     * 那么 返回(然后以下一格位置为原点) 这个位置 即回溯到上一次递归开辟的栈空间中 在这个位置继续向右....
     * @param map  代表地图
     * @param x    代表当前的位置的x轴坐标
     * @param y    代表当前的位置的x轴坐标
     * @return 返回当前路能不能走
     * 行走策略 下->右->上->左  (顺序)
     */
    public static boolean FindWay(int [][]map,int x,int y){
        //如果到达终点了
        if (x == 8&&y == 8){
            return true;
        }
        if (map[x][y] == 0) {
            //标记走的路
            map[x][y] = 2;
            if (FindWay(map, x + 1, y)) {//下
                return true;
            } else if (FindWay(map, x, y + 1)) {//右
                return true;
            } else if (FindWay(map, x - 1, y)) {//上
                return true;
            } else if (FindWay(map, x, y - 1)) {//左
                return true;
            } else {
                return false;
            }
        } else{
            return false;
        }
    }
}

八皇后

public class Queen {
    int []queen = new int[8];
    int [][]queen2 = new int[8][8];
    static int count = 0;
    public static void main(String[] args) {
        Queen q = new Queen();
        q.queen2(0);
        System.out.println(count);
    }
    //八皇后问题 二维数组
    public void queen2(int i){
        if (i==8){
            count++;
//            System.out.println(11);
            erArr.ErInt(queen2);
            System.out.println("-----------");
            return;
        }
        for (int j=0;j<8;j++){

//            System.out.println(judge2(i,j));
            if (judge2(i,j)){
//                System.out.println("11");
                queen2[i][j] = 1;
                queen2(i+1);
                queen2[i][j] = 0;
            }
        }
    }
    //判断验证当前层的皇后有没有跟前面已经放好的皇后产生影响
    public boolean judge2(int x,int y){
        for (int j=0;j<x;j++){
            int z = -1;
            for (int k=0;k<8;k++){
                if (queen2[j][k]==1){
                    z=k;
                }
            }
            if (z==y||x-j == Math.abs(y-z)){
                return false;
            }
        }
        return true;
    }
    //八皇后问题 一维数组解决 i代表第几个皇后
    public void queen(int i){
        if (i==8){//索引从0开始 当他开始放第“8”个的时候 实际上是在放第九个 那代表他前八个已经放好了 那么返回不再往后放
            show();//显示棋盘情况
            count++;
            return;
        }
        //列数
        for (int j=0;j<8;j++){
            //设置第i个皇后的位置为j
            queen[i] = j;
            //然后判断当前皇后是否与之前的冲突 judge方法如果返回true则代表符合要求
            if (judge(i)){
                //如果符合要求 那么放下一个皇后
                queen(i+1);
            }
        }
    }
    //验证当前层的皇后有没有跟前面已经放好的皇后产生影响(在同一行或同一列) 传入的是当前的层数(第几个皇后)
    public boolean judge(int i){
        for (int j=0;j<i;j++){
            //数组queen一共存放8位皇后 相对应的索引代表该皇后所在的行数 对应的索引上面所放着的数字代表他是这一行的第几列
            //如果上面存放的数字相同代表他们在同一列  如果他们行数差 = 列数差 代表他们在同一对角线上面
            if (queen[j] == queen[i]||Math.abs(queen[i]-queen[j]) == (i-j)){
                return false;
            }
        }
        return true;
    }
    //输出当前摆放成功的棋牌
    public void show(){

        for (int i = 0;i < 8 ;i++){
            System.out.print(queen[i]+"\t");
        }
        System.out.println();
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值