谭浩强第五版C程序设计第六章第7题:关于“魔方阵”的问题

题目:

img

我的代码:
写了2个方案,附了方案②运行结果,方案①错的更离谱


#include <stdio.h>

int main() {
    int a[15][15] = {0};
    int i, j, j0, k, k0, n;
    printf("请限定你想输出的魔方阵的组成自然数范围:1~n^2\n请输入n(1~15的奇数):");
    while (1) {
        scanf("%d", &n);
        if (n>=1&&n<=15&&n%2!=0) {//如果n在这个范围并且为奇数
            break;
        }
        else {
            printf("请重新输入:");
        }
    }
    n = n - 1;//行序数=输入行数-1;
    k = n / 2;//初始新列数为中间列:列序数/2
    j = 0;//新行数
    a[j][k] = 1;

    //遍历2~n*n的数,每次循环都会确定一个新位置并存入数值i,保存原位置行列数,然后更新新位置行列数
    for (i = 2; i <= n * n;i++) {

        /*方案①
        //原位置的行数和列数
        j0 = j;
        k0 = k;
        //新位置的行数和列数
        j++;
        k++;
        //就特殊情况进一步更新位置
        if (j0 == 0) {
            j = n;
        }
        if (k0 == n) {
            k = 0;
        }

        if (a[j][k]!=0) {//如果新位置有数
            a[j0+1][k0] = i;//则把数放置老位置的下面
        }
        else if (j0 == 0&&k0==n) {//如果老位置为第0行第m列
            a[j0 + 1][k0] = i;
        }
        else {
            a[j][k] = i;
        }
        */

        //方案②
        //保存前一个数的行列数并更新下一个数的行列数
        j0 = j;//保存前一个数的行数
        if (j==0) {//如果前一个数为第0行
            j = n;//则新行数为n
        }
        else {
            j = j - 1;
        }

        k0 = k;//保存前一个数的列数
        if (k == n) {//如果前一个数为第n列
            k = 0;//则新列数为0
        }
        else {
            k = k + 1;
        }

        if (a[j][k]!=0||j0==0&&k0==n) {//如果按上面规则确定的新行列数元素有数或者上一个数是第一行第n列时
            a[j0+1][k0] = i;//把下一个数放在上一个数的下面,新位置又变为上一个数的下方位置
            j = j0 + 1;
            k = k0;
        }
        else {//否则就把下一个数放在新位置即新的行列数位置
            a[j][k] = i;
        }
    }

    //输出n*n的”魔方阵“
    for (i = 0; i <= n;i++) {
        for (j = 0; j <= n;j++) {
            printf("%5d",a[i][j]);
        }
        printf("\n");
    }
    return 0;
}

我的结果:

img

很迷惑,不知道错哪了