五、回溯算法

1、实验内容
1) 编程实现n皇后问题迭代回溯算法和递归算法。
2、实验要求
2) 通过实例,通过实例理解深度优先策略和回溯机制。

3) 用2-3个实例验证算法和时间复杂度。

NQueen C++算法(递归):

#include<iostream>
#include "math.h"
using namespace std;

class QUEEN
{
public:
	friend int nQueen(int);
	bool Place(int k);
	void Backtrack(int t);
	int n, *x;
	long sum;

};

int nQueen(int n)
{
	QUEEN x;
	x.n = n;
	x.sum = 0;
	int *p = new int[n + 1];
	for (int i = 0; i <= n; i++)
		p[i] = 0;
	x.x = p;
	x.Backtrack(1);
	delete[]p;

	return x.sum;

}

bool QUEEN::Place(int k)
{
	for (int j = 1; j<k; j++)
		if ((abs(k - j) == abs(x[j] - x[k])) || (x[j] == x[k]))
			return false;
	return true;
}

void QUEEN::Backtrack(int t)
{
	if (t > n){
		sum++;
		cout << "n皇后问题的第" << sum << "个" << "可行解的坐标为:" << endl;
		for (t = 1; t <= n; t++)
			cout << "( " << t << "," << x[t] << ")" << endl;
		cout << "********" << endl;
	}

	else
		for (int i = 1; i <= n; i++)
		{
		x[t] = i;
		if (Place(t))
			Backtrack(t + 1);//递归求解
		}
}
void  main()
{
	int n;
	cout << "***************N 皇后问题*************** " << endl;
	cout << endl;
	cout << "请输入皇后的个数 n:  " << endl;
	cin >> n;
	cout << nQueen(n) << endl;
	system("pause");
}

NQueen java算法:

import java.util.Scanner;
public class NQueen {
	static int n;
	static int[]x;
	static long sum;
	
	public static void main(String []args){
		Scanner input = new Scanner(System.in);
		int n = input.nextInt();
		System.out.println(nQueen(n));
	}
	
	public static long nQueen(int nn){
		n =nn;
		sum =0;
		x = new int[n+1];
		for(int i =0;i<=n;i++)
		x[i]=0;
		backtrace();
		return sum;
	}
	private static boolean place (int k){
		for(int j =1;j<k;j++)
			if((Math.abs(k-j)==Math.abs(x[j]-x[k]))||(x[j]==x[k]))
		return false;
		return true;
	}
	
	private static void backtrace()
	{
		x[1]=0;
		int k =1;
		while(k>0){
			x[k]+=1;
			while((x[k]<=n)&&!(place(k)))
				x[k]+=1;
			if(x[k]<=n)
				if(k==n){
					sum++;
					System.out.print("第"+sum+"个解为");
					for(int i =1;i<=n;i++){
						System.out.print(x[i]+" ");
					}
					System.out.println(" ");
				}
			
				else{
					k++;
					x[k]=0;
				}
			else k--;
		}
	}
}

另:
public class Backtracking2 {
	private static int number;
	private static int[] chessboard;
	private static int totalSolution;

	public static int NQueen(int num) {
		number = num;
		chessboard = new int[number + 1];
		totalSolution = 0;

		for (int i = 0; i < number + 1; i++) {
			chessboard[i] = 0;
		}
		backtrack();
		return totalSolution;
	}

	public static boolean isPlaceable(int index) {
		if (index <= 0) {
			try {
				throw new Exception("Illegal index!");
			} catch (Exception e) {
				e.printStackTrace();
			}
		}
		for (int i = 1; i < index; i++) {
			// 1.检测index和i是否在同一对角线上
			// 2.检测index和i是否同列同行
			if ((Math.abs(index - i) == Math.abs(chessboard[index]
					- chessboard[i]))
					|| (chessboard[i] == chessboard[index])) {
				return false;
			}
		}
		return true;
	}

	public static void backtrack() {
		chessboard[1] = 0;
		int index = 1;
		while (index > 0) {
			chessboard[index] += 1;
			while (!(isPlaceable(index)) && (chessboard[index] <= number)) {
				chessboard[index] += 1;
			}
			if (chessboard[index] <= number) {
				if (index == number) {
					totalSolution++;
					for (int i = 1; i <= number; i++) {
						System.out.print(i + " " + chessboard[i] + "     ");
					}
					System.out.println("");
				} else {
					index++;
					chessboard[index] = 0;
				}
			} else {
				index--;
			}
		}
	}

	public static void main(String[] args) {
		Backtracking2 demo = new Backtracking2();
		demo.NQueen(8);
		System.out.println(number + "皇后问题总解数有" + totalSolution + "个:");
	}
}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值