幻方

package 幻方;
import java.util.Scanner;
/**
 * 目前使用数组实现,但是考虑将来可以缩减时间复杂度,增加空间复杂度
 * 减少循环相乘次数
 * 
 * 具体来说使用循环去除变量中不必要参加循环的数据,可以节省很多次计算
 * 16x16x16x16 - 16x15x14x13等,比起增加的设置时间
 * 
 *  
 *
 */
public class Main {
	int arr[] = new int[26];
	boolean arr2[] = new boolean[26];

	int i = 0;
	int p =0;
	static int k = 0, ak = 0;

	public static void main(String[] args) {
		Scanner input = new Scanner(System.in);
		ak = input.nextInt();
		input.close();
		Main aa = new Main();
 
		if(ak>35) {
			aa.p=5;
			k=35;
		}
		if(ak>69) {
			aa.p=7;
			k=69;
		}
		
		for (int i = 1; i <= 20; i++) {
			aa.arr[i - 1] = 19;
			aa.arr2[i - 1] = false;
		}
		aa.ff(0);
	 
	}

	boolean b = false;

	private void ff(int line) {

		if (line == 4) {
			k++;
			if (k == ak) {
				b = true;
				for (int i1 = 0; i1 <= 3; i1++) {
					for (int j4 = 0; j4 <= 3; j4++)
						System.out.print(arr[i1 * 4 + j4] + " ");
					System.out.println();
				}
			}
		}
		if (line == 4 || b) {
			this.clear((line - 1) * 4 + 0);
			return;
		}

		for (int i = 1; i <= 16; i++) {

			arr2[arr[line * 4 + 0]] = false;

			if (arr2[i])
				continue;

			arr[line * 4 + 0] = i;

			if (line == 3) {
				if (arr[3] + arr[6] + arr[9] + arr[12] != 34)
					continue;
				if (arr[0] + arr[4] + arr[8] + arr[12] != 34)
					continue;
			}
			arr2[i] = true;
			if(line >0)
				p =0;
			for (int j = p; j <= 16; j++) {
			
				arr2[arr[line * 4 + 1]] = false;
				if (arr2[j])
					continue;
				arr[line * 4 + 1] = j;

				if (line == 3) {
					if (arr[1] + arr[5] + arr[9] + arr[13] != 34)
						continue;
				}
				arr2[j] = true;
				for (int j2 = 1; j2 <= 16; j2++) {
					arr2[arr[line * 4 + 2]] = false;
					if (arr2[j2])
						continue;
					arr[line * 4 + 2] = j2;
					if (line == 3) {
						if (arr[2] + arr[6] + arr[10] + arr[14] != 34)
							continue;
					}
					arr2[j2] = true;
					for (int j3 = 1; j3 <= 16; j3++) {
						arr2[arr[line * 4 + 3]] = false;
						if (arr2[j3])
							continue;
						arr[line * 4 + 3] = j3;

						if (arr[line * 4 + 0] + arr[line * 4 + 1]
								+ arr[line * 4 + 2] + arr[line * 4 + 3] != 34)
							continue;

						if (line == 3) {
							if (arr[3] + arr[7] + arr[11] + arr[15] != 34)
								continue;
							if (arr[0] + arr[5] + arr[10] + arr[15] != 34)
								continue;
						}
						arr2[j3] = true;
						ff(line + 1);
					}
				}
			}
		}
		this.clear(line * 4 + 0);
	}

	private void clear(int n) {
		//TODO: 必须n-1 ,否则 3的取值不同
		for (int i = n-1; i <= 15; i++)
			if(i>-1)
			arr2[arr[i]] = false;
	}
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值