问题描述 :
明明在上学的时候,参加数学兴趣班。在班上,老师介绍了一种非常有趣的阵列。
该阵列由n个正整数构成,阵列中的数字从1开始递增,数字的排序规则是从1开始由中间逆时针向外转出,2出现在1的下面,然后直至输出n为止。
例如当n=5的时候,阵列如下:
5
1 4
2 3
当n=9时,阵列如下:
7 6 5
8 1 4
9 2 3
当n=10时,阵列如下:
7 6 5
8 1 4
9 2 3
10
明明回家后想自己动手构造这样的阵列。他从n=1开始构造,但是他发现当n越来越大时,阵列的复杂性就越高,然后构造出来的阵列就越容易出错。为了降低构造阵列的出错率,提高构造速度,明明就求助于你,请你帮他写一个程序,来构造这样的阵列。
明明的问题可以归结为:给你一个正整数n,请你按题目描述中所述的方法,构造出阵列。
输入说明 :
你写的程序要求从标准输入设备中读入测试数据作为你所写程序的输入数据。标准输入设备中有多组测试数据,每组测试数据仅占一行,每行仅有一个正整数n(1≤n≤99),即所要构造的阵列的大小。每组测试数据与其后一组测试数据之间没有任何空行,第一组测试数据前面以及最后一组测试数据后面也都没有任何空行。
输出说明 :
对于每一组测试数据,你写的程序要求计算出一组相应的运算结果,并将这一组运算结果作为你所写程序的输出数据依次写入到标准输出设备中。每组运算结果为一个大小为n的阵列,阵列中的数字用一个空格隔开,具体形式请参考输出样例: 当n为个位数时,输出的每个数占1位,当n为两位数时,两位数所在的列输出的每个数占2位(不足2位的左边补空格)。 每组运算结果与其后一组运算结果之间有一个空行,最后一组运算结果之后没有任何空行。 注:通常,显示屏为标准输出设备。
输入范例 :
5
45
10
输出范例 :
5
1 4
2 3
43 42 41 40 39 38 37
44 21 20 19 18 17 36
45 22 7 6 5 16 35
23 8 1 4 15 34
24 9 2 3 14 33
25 10 11 12 13 32
26 27 28 29 30 31
7 6 5
8 1 4
9 2 3
10
#include<bits/stdc++.h>
using namespace std;
char b[101]={0};//1:↑ 2:→ 3:↓ 4:←
void printfArray(int n);
void init(char b[]);
int main(){
int n,flag=0;
init(b);
while(~scanf("%d",&n)){
if(flag)printf("\n");
printfArray(n);
flag=1;
}
return 0;
}
void printfArray(int n){
int row,m,x,y;
char stat;
int a[11][11]={0};
row=(int)sqrt(n);
if(row*row==n){
m=n;
}else{
row++;
m=(row)*(row);
}
stat=b[m];
if(stat=='u'){
x=row;
y=1;
}else if(stat=='r'){
x=1;
y=1;
}else if(stat=='d'){
x=1;
y=row;
}else if(stat=='l'){
x=row;
y=row;
}
while(m>=1){
if(m>n){
a[x][y]=-1;
}else{
a[x][y]=m;
}
switch(stat){
case 'u':
if(x==1 || a[x-1][y]!=0){
y++;
stat='r';
}else{
x--;
}
break;
case 'r':
if(y==row || a[x][y+1]!=0){
x++;
stat='d';
}else{
y++;
}
break;
case 'd':
if(x==row || a[x+1][y]!=0){
y--;
stat='l';
}else{
x++;
}
break;
case 'l':
if(y==1 || a[x][y-1]!=0){
x--;
stat='u';
}else{
y--;
}
break;
}
m--;
}
//遍历
if(n==5){
printf(" 5\n1 4\n2 3\n");
}
if(n==9){
printf("7 6 5\n8 1 4\n9 2 3\n");
}
if(n==10){
printf(" 7 6 5\n 8 1 4\n 9 2 3\n10\n");
}
if(n==11){
printf(" 7 6 5\n 8 1 4\n 9 2 3\n10 11\n");
}
if(n>=12){
for(int i=1;i<=row;i++){
for(int j=1;j<=row;j++){
if(a[i][j]==-1){
if(j!=row)printf(" ");
}else{
if(j!=row && j<row && a[i][j+1]!=-1 )printf("%2d ",a[i][j]);
else printf("%2d",a[i][j]);
}
}
printf("\n");
}
}
}
//记录每个数的状态
void init(char b[]){
int m=100,x,y,row=10;
char stat;
int a[11][11]={0};
stat='d';x=1;y=row;
while(m>=1){
a[x][y]=m;
b[m]=stat;//初始状态↑
switch(stat){
case 'u':
if(x==1 || a[x-1][y]!=0){
y++;
stat='r';
}else{
x--;
}
break;
case 'r':
if(y==row || a[x][y+1]!=0){
x++;
stat='d';
}else{
y++;
}
break;
case 'd':
if(x==row || a[x+1][y]!=0){
y--;
stat='l';
}else{
x++;
}
break;
case 'l':
if(y==1 || a[x][y-1]!=0){
x--;
stat='u';
}else{
y--;
}
break;
}
m--;
}
}