标题:四阶幻方

把1~16的数字填入4x4的方格中,使得行、列以及两个对角线的和都相等,满足这样的特征时称为:四阶幻方。

四阶幻方可能有很多方案。如果固定左上角为1,请计算一共有多少种方案。
比如: 以及: 就可以算为两种不同的方案。 请提交左上角固定为1时的所有方案数字,不要填写任何多余内容或说明文字。

记:

一开始直接用dfs搜索,发现时间太长,于是找规律

发现,幻方的值,为1累加到16的和除以阶数4

(所以类似的n阶幻方也可以这么做?)

另外一个3阶的题目用同样方法也行

http://www.cnblogs.com/mind000761/p/8595390.html

从而添加剪枝操作后,运行时间约1min

示例代码:

 #include <stdio.h>
#define MAX 16 /*可放置的最大数*/
#define N 4 /*阶数*/ int key = ; /*1到MAX的累加和除以MAX*/
int count = ; /*满足条件的解*/
int arr[N+][N+] = {};
int f[MAX+] = {}; void dfs(int x)
{
int i,j,k,s; /*s用于剪枝操作*/ if (x > MAX)
{
i = arr[][]+arr[][]+arr[][]+arr[][];
j = arr[][]+arr[][]+arr[][]+arr[][];
if (i != key || j != key)
{
return;
}
for (i = ; i <= N ; i ++)
{
s = ;
for (j = ; j <= N ; j ++)
{
s += arr[j][i];
}
if (s != key)
{
return;
}
} count ++;
return;
} for (i = ; i <= MAX ; i ++)/*遍历2-MAX*/
{
if (!f[i])
{
for (j = ; j <= N ; j ++)
{
s = ;
for (k = ; k <= N ; k ++)
{
if (!arr[j][k])
{
f[i] = ;
arr[j][k] = i;
break;
}
s += arr[j][k];
}
if (f[i])
{
break;
}
if (s != key)
{
return;
}
}
dfs(x+);
arr[j][k] = ;
f[i] = ;
}
} return ;
} int main(void)
{
f[] = ;
arr[][] = ;
dfs();
printf("%d",count);/**/
return ;
}
05-11 16:11