这些方法是由我们老师提供的:
一、奇数阶
1.首先填第一行中间位置。
2.然后向其右上方填数。
3.如果该数是n的倍数,则放在 上一个数 的正下方.
二、双偶阶 n=4*k
1.把矩阵按照 1-n*n的顺序 从左到右 从上到下 事先写好。
2.把 矩阵 分成 若干个 4*4的小块。
3.每一块都关于 中心点 中心对称交换。
三、单偶阶 n=4*k+2
1.把矩阵分成四块,每块有 2*k+1个。
2.按照 左上 右下 右上 左下 的顺序,以奇数阶矩阵的规律 填好 1-n*n个数字。
3.根据以下规则进行调换:
①右半两个小矩阵中 大于 k+2列 上下交换
②左半两个小矩阵中位于(k+1,k+1)的格位 上下交换
③左半两个小矩阵中 除了 (k+1,1)的格子 之外,小于k+1的列 上下交换
具体代码+注释:
#include <bits/stdc++.h>
//#include <algorithm>
using namespace std;
typedef long long ll;
const int maxn=1e3+5;
int num[maxn][maxn];
int cop[maxn][maxn];
int n;
void odd_matrix()//奇数阶
{
int mid=n/2;//确定中间元素位置
int tot=0;
int y=mid,x=0;//更新每一步的位置
while(tot<n*n)
{
num[x][y]=++tot;
if(tot%n==0)//如果该位置是n的倍数,则放在该数位置的下一行
{
y=y;
x=(x+1)%n;
}
else
{
x=(x-1+n)%n;//否则放在左上方
y=(y+1)%n;
}
}
for(int i=0;i<n;i++)
{
for(int k=0;k<n;k++)
printf("%4d",num[i][k]);
printf("\n");
}
}
void even_matrix_4k()
{
int tot=0;
for(int i=1;i<=n;i++)
for(int k=1;k<=n;k++)
num[i][k]=cop[i][k]=++tot;//先按原方向排排满
for(int i=1;4*i-3<=n;i++)
{
for(int k=1;k<=n;k++)
{
int tempx=4*i-3;//确定每块分成的行
int tempy=k;//确定每一块分成的列
if(k%4==1)
{
int cir=4;
while(cir--)
{
num[tempx][tempy]=cop[n-tempx+1][n-tempy+1];//与他 中心对称 的另一半进行交换
tempx++;tempy++;
}
}
else if(k%4==0)
{
int cir=4;
while(cir--)
{
num[tempx][tempy]=cop[n-tempx+1][n-tempy+1];//因为这种写法考虑到 全局的 交换 所以不应该使用 swap交换两个位置
tempx++;tempy--;
}
}
}
}
for(int i=1;i<=n;i++)
{
for(int k=1;k<=n;k++)
printf("%5d",num[i][k]);
printf("\n");
}
}
void help_add()
{
int tot=0;
int cnt=n/2;
int y=cnt/2,x=0;
while(tot<cnt*cnt)
{
num[x][y]=++tot;
if(tot%cnt==0)//如果该位置是n的倍数,则放在该数位置的下一行
{
y=y;
x=(x+1)%cnt;
}
else
{
x=(x-1+cnt)%cnt;//否则放在左上方
y=(y+1)%cnt;
}
}
y=cnt/2+cnt;x=cnt;
while(tot<2*cnt*cnt)
{
num[x][y]=++tot;
if(tot%cnt==0)//如果该位置是n的倍数,则放在该数位置的下一行
{
y=y;
x=(x+1)%cnt+cnt;
}
else
{
x=(x-1+cnt)%cnt+cnt;//否则放在左上方
y=(y+1)%cnt+cnt;
}
}
y=cnt/2+cnt;x=0;
while(tot<3*cnt*cnt)
{
num[x][y]=++tot;
if(tot%cnt==0)//如果该位置是n的倍数,则放在该数位置的下一行
{
y=y;
x=(x+1)%cnt;
}
else
{
x=(x-1+cnt)%cnt;//否则放在左上方
y=(y+1)%cnt+cnt;
}
}
y=cnt/2;x=cnt;
while(tot<4*cnt*cnt)
{
num[x][y]=++tot;
if(tot%cnt==0)//如果该位置是n的倍数,则放在该数位置的下一行
{
y=y;
x=(x+1)%cnt+cnt;
}
else
{
x=(x-1+cnt)%cnt+cnt;//否则放在左上方
y=(y+1)%cnt;
}
}
}
void even_matrix_4kmod2()
{
help_add();
int k=n/4;//确定k
int cnt=n/2;
for(int i=k+2+cnt;i<n;i++)
for(int j=0;j<cnt;j++)
swap(num[j][i],num[cnt+j][i]);//大于k+2的需要交换
swap(num[k][k],num[n-1-k][k]);
for(int i=0;i<k;i++)
{
for(int j=0;j<cnt;j++)
{
if(i==0&&j==k) continue;//特例考虑
swap(num[j][i],num[cnt+j][i]);//其余的上下交换
}
}
for(int i=0;i<n;i++)
{
for(int k=0;k<n;k++)
printf("%5d",num[i][k]);
printf("\n");
}
}
int main()
{
printf("请输入魔方矩阵的阶数: ");
scanf("%d",&n);
if(n%2==1)
odd_matrix();
else if(n%4==0)
even_matrix_4k();
else if(n%4==2)
even_matrix_4kmod2();
else
printf("不存在该矩阵");
return 0;
}
谢谢阅读。