Live2D
Fork me on GitHub

12、递归-八皇后问题

来源:https://www.bilibili.com/video/BV1B4411H76f?p=39

一、问题描述

8*8的一个棋盘,放置8个棋子,按照规则,相互之间不在同一行,同一列,同一斜线

思路如下:

  在第一个位置(0,0)放置第一个皇后

  判断(1,1)是否合适放第二个,不合适继续尝试(1,3)

  得到一个正解后回溯,得到第一个位置(0,0)放置第一个皇后的结果

  将第一个皇后放到别的位置(例如(0,1))得到另一种解决方案

理论上用一个一维数组就可以代表整个棋盘,因为棋盘的行列是不可重复的,每一行或者每一列只能放置一个皇后

  

二、实现

注意:进行判断的时候判断的是当前的下标为n的皇后与之前的皇后是否冲突

      在放置皇后的时候,这里用n来表示初始的是在第n行,

 1 public class Queue8 {
 2     int max = 8;//皇后
 3     int[] array = new int[8];//棋盘
 4     static int count = 0;//解决方案的数目
 5 
 6     public static void main(String[] args) {
 7         Queue8 queue8 = new Queue8();
 8         queue8.check(0);
 9         System.out.println(count);
10     }
11 
12     //放置皇后在不同的位置
13     private void check(int n){
14         if(n == max){
15             count++;
16             for (int i = 0; i < array.length; i++) {
17                 System.out.print(array[i]+"");
18             }
19             System.out.println();
20             return;
21         }
22 
23         for (int i = 0; i < max; i++) {
24             array[n] = i;//放置在第n行i列
25             if(judge(n)){
26                 //没有冲突的,继续下一行看放在第几列不冲突
27                 check(n+1);
28             }
29         }
30     }
31 
32     //检查放置第n个皇后是否与之前的冲突
33     //这里用了一个数组代替整个棋盘,代表了行不冲突,
34     // 数组的内容是皇后处于哪个列,这个列不冲突需要判断,斜线不冲突也要判断
35     private boolean judge(int n){
36         for (int i = 0; i < n; i++) {
37             //array[i] == array[n]列存在冲突
38             //Math.abs(n-i) == Math.abs(array[n] - array[i])斜线上冲突
39             if(array[i] == array[n] || Math.abs(n-i) == Math.abs(array[n] - array[i])){
40                 return false;
41             }
42         }
43         return true;
44     }
45 
46 
47 }

结果,一共有92种放置方法。

04752613
05726314
06357142
06471352
13572064
14602753
14630752
15063724
15720364
16257403
16470352
17502463
20647135
24170635
24175360
24603175
24730615
25147063
25160374
25164073
25307461
25317460
25703641
25704613
25713064
26174035
26175304
27360514
30471625
30475261
31475026
31625704
31625740
31640752
31746025
31750246
35041726
35716024
35720641
36074152
36271405
36415027
36420571
37025164
37046152
37420615
40357162
40731625
40752613
41357206
41362750
41506372
41703625
42057136
42061753
42736051
46027531
46031752
46137025
46152037
46152073
46302751
47302516
47306152
50417263
51602473
51603742
52064713
52073164
52074136
52460317
52470316
52613704
52617403
52630714
53047162
53174602
53602417
53607142
57130642
60275314
61307425
61520374
62057413
62714053
63147025
63175024
64205713
71306425
71420635
72051463
73025164
92

我感觉整个过程有意思的地方就是回溯到我们给定了的初始0这个位置,但是初始值0(第0行)所有i为0(第0列)的情况都尝试过了,继续进入了第一个皇后放置在i=1(第0行1列)的情况尝试。最终尝试了所有的可能

 

 

 

posted @ 2020-06-18 15:26  -小二黑-  阅读(181)  评论(0编辑  收藏  举报