N皇后问题java实现
N皇后问题是一个典型的约束求解问题,利用递归机制,可以很快的得到结果。
N皇后问题的描述:
在一个n*n的棋盘上,摆放n个皇后,要求每个皇后所在行、列、以及两个对角线上不能出现其他的皇后,否则这些皇后之间将会相互攻击。如下图所示。
利用递归机制,可以很容易的求解n皇后问题。针对八皇后,总共有92种解。下面将给出N-皇后问题的一般求解代码,在这里代码是使用java编码的。
总共设计了三个类,一个是皇后类(Queen),一个棋盘类(Board),一个是求解主程序类(NQueens)。具体代码如下:
1: import java.util.ArrayList;
2: import java.util.List;
3:
4: public class NQueens {
5:
6: private int numSolutions;//求解结果数量
7: private int queenSize;//皇后的多少
8: private Board board;//棋盘
9: private List<Queen> queens = new ArrayList<Queen>();//皇后
10: //private List<Queen> nQueens = new ArrayList<Queen>();
11:
12: public NQueens(){
13:
14: }
15:
16: public NQueens(int size){
17: numSolutions = 0;
18: queenSize = size;
19: board = new Board(queenSize);
20: for (int i = 0; i < queenSize; i++) {
21: Queen queen = new Queen();
22: queens.add(queen);
23: }
24:
25: }
26:
27: public void solve(){
28: System.out.println("Start solve....");
29: putQueen(0);
30: }
31:
32: private void putQueen(int index){
33:
34: int row = index;
35: //如果此列可用
36: for (int col = 0; col < board.getQueenSize(); col++) {
37: if (board.getLayout()[row][col] == 0) {
38: //将皇后的位置置为此列位置
39: queens.get(row).setPosition(col);
40: //然后将相应的位置(此列的正下方以及两个对角线)加1(即使其不可用)
41: for (int i = row + 1; i < board.getQueenSize(); i++) {
42: board.getLayout()[i][col] ++;
43: if (row + col - i >= 0) {
44: board.getLayout()[i][row + col - i] ++;
45: }
46: if (i + col - row < board.getQueenSize()) {
47: board.getLayout()[i][i + col - row] ++;
48: }
49: }
50:
51: if (row == board.getQueenSize()-1) {
52: numSolutions++;
53: printSolution(numSolutions);
54: }else {
55: putQueen(row + 1);
56: }
57: //回溯,将相应的位置(此列的正下方以及两个对角线)减1
58: for (int i = row + 1; i < board.getQueenSize(); i++) {
59: board.getLayout()[i][col] --;
60: if (row + col - i >= 0) {
61: board.getLayout()[i][row + col - i] --;
62: }
63: if (i + col - row < board.getQueenSize()) {
64: board.getLayout()[i][i + col - row] --;
65: }
66: }
67:
68: }
69: }
70: }
71: //打印求解结果
72: private void printSolution(int i){
73: System.out.println("The "+i+ " solution is:");
74: for (int j = 0; j < board.getQueenSize(); j++) {
75: for (int k = 0; k < board.getQueenSize(); k++) {
76: System.out.print(queens.get(j).getPosition() == k ? " * ":" - ");
77: }
78: System.out.println();
79: }
80: System.out.println();
81: }
82: /**
83: * @param args
84: */
85: public static void main(String[] args) {
86: //可以改变参数
87: NQueens nQueens = new NQueens(8);
88: nQueens.solve();
89:
90: }
91:
92:
93:
94: }
95: import java.io.Serializable;
96:
97: //皇后类
98: public class Queen implements Serializable, Cloneable {
99:
100: /**
101: *
102: */
103: private static final long serialVersionUID = 7354459222300557644L;
104: //皇后的位置
105: private int position;
106:
107: public Queen(){
108:
109: }
110:
111: public int getPosition() {
112: return position;
113: }
114:
115: public void setPosition(int position) {
116: this.position = position;
117: }
118:
119: public Object clone() throws CloneNotSupportedException {
120:
121: return super.clone();
122: }
123: }
124:
125: import java.io.Serializable;
126:
127: //棋盘类
128: public class Board implements Serializable,Cloneable {
129:
130: /**
131: *
132: */
133: private static final long serialVersionUID = -2530321259544461828L;
134:
135: //棋盘的大小
136: private int queenSize;
137:
138: //棋盘的布局
139: private int[][] layout;
140:
141: public Board(int size){
142: this.queenSize = size;
143: this.layout = new int[queenSize][queenSize];
144: //初始化,使棋盘所有位置都可用,即全部置为0
145: for (int i = 0; i < queenSize; i++) {
146: for (int j = 0; j < queenSize; j++) {
147: layout[i][j] = 0;
148:
149: }
150: }
151: }
152:
153: public int getQueenSize() {
154: return queenSize;
155: }
156:
157: public void setQueenSize(int queenSize) {
158: this.queenSize = queenSize;
159: }
160:
161: public int[][] getLayout() {
162: return layout;
163: }
164:
165: public void setLayout(int[][] layout) {
166: this.layout = layout;
167: }
168:
169: public Object clone() throws CloneNotSupportedException {
170:
171: return super.clone();
172: }
173:
174: }
175:
作者:Alex Yu
出处:http://www.cnblogs.com/biaoyu/
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。