• 递归、迷宫问题、八皇后


    递归调用机制

     1 public class RecursionTest {
     2 
     3     public static void main(String[] args) {
     4         // TODO Auto-generated method stub
     5         //通过打印问题,回顾递归调用机制
     6         test(4);
     7         
     8         //int res = factorial(3);
     9         //System.out.println("res=" + res);
    10     }
    11     //打印问题. 
    12     public static void test(int n) {
    13         if (n > 2) {
    14             test(n - 1);
    15         } //else {
    16             System.out.println("n=" + n);
    17         // }
    18     }
    19     //阶乘问题
    20     public static int factorial(int n) {
    21         if (n == 1) { 
    22             return 1;
    23         } else {
    24             return factorial(n - 1) * n; // 1 * 2 * 3
    25         }
    26     }
    27 
    28 
    29 }

    递归求最大值

     1 public class Text {
     2     public static void main(String[] args) {
     3         int arr[] = new int[] {1,34,5,4,32,2,38,6,7,8};
     4         int Max= mergeSort(arr,0,arr.length-1);
     5         for(int i = 0; i< arr.length; i++) {
     6         System.out.println(arr[i]);
     7     }
     8         
     9         System.out.println(Max);
    10     }
    11     
    12     public static int mergeSort(int[] arr, int l, int r) {
    13     if (l == r) {
    14         return arr[l];
    15     }
    16     int mid = ((r + l) >> 1);
    17     int Getrmax = mergeSort(arr, l, mid);
    18     int Fetlmax = mergeSort(arr, mid+1, r);
    19     return Math.max(Getrmax, Fetlmax);
    20     }
    21     
    22 }

    猴子吃桃

     1 public class Text2 {
     2     //猴子吃桃问题
     3     public static int tao(int n) {
     4         if(n == 10) {  // 终止条件
     5             return 1;
     6         }
     7         return (tao(n + 1) + 1 * 2); // 把范围缩小到最小  两天 求变大时
     8         
     9     }
    10     public static void main(String[] args) {
    11         System.out.println(tao(1));
    12     }
    13 }

    回溯问题

      1 public class MiGong {
      2 
      3     public static void main(String[] args) {
      4         // 先创建一个二维数组,模拟迷宫
      5         // 地图
      6         int[][] map = new int[8][7];
      7         // 使用1 表示墙
      8         // 上下全部置为1
      9         for (int i = 0; i < 7; i++) {
     10             map[0][i] = 1;
     11             map[7][i] = 1;
     12         }
     13 
     14         // 左右全部置为1
     15         for (int i = 0; i < 8; i++) {
     16             map[i][0] = 1;
     17             map[i][6] = 1;
     18         }
     19         //设置挡板, 1 表示
     20         map[3][1] = 1;
     21         map[3][2] = 1;
     22 //        map[1][2] = 1;
     23 //        map[2][2] = 1;
     24         
     25         // 输出地图
     26         System.out.println("地图的情况");
     27         for (int i = 0; i < 8; i++) {
     28             for (int j = 0; j < 7; j++) {
     29                 System.out.print(map[i][j] + " ");
     30             }
     31             System.out.println();
     32         }
     33         
     34         //使用递归回溯给小球找路
     35         //setWay(map, 1, 1);
     36         setWay2(map, 1, 1);
     37         
     38         //输出新的地图, 小球走过,并标识过的递归
     39         System.out.println("小球走过,并标识过的 地图的情况");
     40         for (int i = 0; i < 8; i++) {
     41             for (int j = 0; j < 7; j++) {
     42                 System.out.print(map[i][j] + " ");
     43             }
     44             System.out.println();
     45         }
     46         
     47     }
     48     
     49     //使用递归回溯来给小球找路
     50     //说明
     51     //1. map 表示地图
     52     //2. i,j 表示从地图的哪个位置开始出发 (1,1)
     53     //3. 如果小球能到 map[6][5] 位置,则说明通路找到.
     54     //4. 约定: 当map[i][j] 为 0 表示该点没有走过 当为 1 表示墙  ; 2 表示通路可以走 ; 3 表示该点已经走过,但是走不通
     55     //5. 在走迷宫时,需要确定一个策略(方法) 下->右->上->左 , 如果该点走不通,再回溯
     56     /**
     57      * 
     58      * @param map 表示地图
     59      * @param i 从哪个位置开始找
     60      * @param j 
     61      * @return 如果找到通路,就返回true, 否则返回false
     62      */
     63     public static boolean setWay(int[][] map, int i, int j) {
     64         if(map[6][5] == 2) { // 通路已经找到ok
     65             return true;
     66         } else {
     67             if(map[i][j] == 0) { //如果当前这个点还没有走过
     68                 //按照策略 下->右->上->左  走
     69                 map[i][j] = 2; // 假定该点是可以走通.
     70                 if(setWay(map, i+1, j)) {//向下走
     71                     return true;
     72                 } else if (setWay(map, i, j+1)) { //向右走
     73                     return true;
     74                 } else if (setWay(map, i-1, j)) { //向上
     75                     return true;
     76                 } else if (setWay(map, i, j-1)){ // 向左走
     77                     return true;
     78                 } else {
     79                     //说明该点是走不通,是死路
     80                     map[i][j] = 3;
     81                     return false;
     82                 }
     83             } else { // 如果map[i][j] != 0 , 可能是 1, 2, 3
     84                 return false;
     85             }
     86         }
     87     }
     88     
     89     //修改找路的策略,改成 上->右->下->左
     90     public static boolean setWay2(int[][] map, int i, int j) {
     91         if(map[6][5] == 2) { // 通路已经找到ok
     92             return true;
     93         } else {
     94             if(map[i][j] == 0) { //如果当前这个点还没有走过
     95                 //按照策略 上->右->下->左
     96                 map[i][j] = 2; // 假定该点是可以走通.
     97                 if(setWay2(map, i-1, j)) {//向上走
     98                     return true;
     99                 } else if (setWay2(map, i, j+1)) { //向右走
    100                     return true;
    101                 } else if (setWay2(map, i+1, j)) { //向下
    102                     return true;
    103                 } else if (setWay2(map, i, j-1)){ // 向左走
    104                     return true;
    105                 } else {
    106                     //说明该点是走不通,是死路
    107                     map[i][j] = 3;
    108                     return false;
    109                 }
    110             } else { // 如果map[i][j] != 0 , 可能是 1, 2, 3
    111                 return false;
    112             }
    113         }
    114     }
    115 
    116 }

    作业:

      

    //待添加

     八皇后问题

     1 public class Queue8 {
     2 
     3     //定义一个max表示共有多少个皇后
     4     int max = 8;
     5     //定义数组array, 保存皇后放置位置的结果,比如 arr = {0 , 4, 7, 5, 2, 6, 1, 3} 
     6     int[] array = new int[max];
     7     static int count = 0;
     8     static int judgeCount = 0;
     9     public static void main(String[] args) {
    10         //测试一把 , 8皇后是否正确
    11         Queue8 queue8 = new Queue8();
    12         queue8.check(0);
    13         System.out.printf("一共有%d解法", count);
    14         System.out.printf("一共判断冲突的次数%d次", judgeCount); // 1.5w
    15         
    16     }
    17     
    18     
    19     
    20     //编写一个方法,放置第n个皇后
    21     //特别注意: check 是 每一次递归时,进入到check中都有  for(int i = 0; i < max; i++),因此会有回溯
    22     private void check(int n) {
    23         if(n == max) {  //n = 8 , 其实8个皇后就既然放好
    24             print();
    25             return;
    26         }
    27         
    28         //依次放入皇后,并判断是否冲突
    29         for(int i = 0; i < max; i++) {
    30             //先把当前这个皇后 n , 放到该行的第1列
    31             array[n] = i;
    32             //判断当放置第n个皇后到i列时,是否冲突
    33             if(judge(n)) { // 不冲突
    34                 //接着放n+1个皇后,即开始递归
    35                 check(n+1); //  
    36             }
    37             //如果冲突,就继续执行 array[n] = i; 即将第n个皇后,放置在本行得 后移的一个位置
    38         }
    39     }
    40     
    41     //查看当我们放置第n个皇后, 就去检测该皇后是否和前面已经摆放的皇后冲突
    42     /**
    43      * 
    44      * @param n 表示第n个皇后
    45      * @return
    46      */
    47     private boolean judge(int n) {
    48         judgeCount++;
    49         for(int i = 0; i < n; i++) {
    50             // 说明
    51             //1. array[i] == array[n]  表示判断 第n个皇后是否和前面的n-1个皇后在同一列
    52             //2. Math.abs(n-i) == Math.abs(array[n] - array[i]) 表示判断第n个皇后是否和第i皇后是否在同一斜线
    53             // n = 1  放置第 2列 1 n = 1 array[1] = 1
    54             // Math.abs(1-0) == 1  Math.abs(array[n] - array[i]) = Math.abs(1-0) = 1
    55             //3. 判断是否在同一行, 没有必要,n 每次都在递增
    56             if(array[i] == array[n] || Math.abs(n-i) == Math.abs(array[n] - array[i]) ) {
    57                 return false;
    58             }
    59         }
    60         return true;
    61     }
    62     
    63     //写一个方法,可以将皇后摆放的位置输出
    64     private void print() {
    65         count++;
    66         for (int i = 0; i < array.length; i++) {
    67             System.out.print(array[i] + " ");
    68         }
    69         System.out.println();
    70     }
    71 
    72 }
  • 相关阅读:
    B.Icebound and Sequence
    Educational Codeforces Round 65 (Rated for Div. 2) D. Bicolored RBS
    Educational Codeforces Round 65 (Rated for Div. 2) C. News Distribution
    Educational Codeforces Round 65 (Rated for Div. 2) B. Lost Numbers
    Educational Codeforces Round 65 (Rated for Div. 2) A. Telephone Number
    Codeforces Round #561 (Div. 2) C. A Tale of Two Lands
    Codeforces Round #561 (Div. 2) B. All the Vowels Please
    Codeforces Round #561 (Div. 2) A. Silent Classroom
    HDU-2119-Matrix(最大匹配)
    读书的感想!
  • 原文地址:https://www.cnblogs.com/yaozhenhua/p/11209343.html
Copyright © 2020-2023  润新知