蛇形环形矩阵
蛇形环形矩阵是一种从外到里或者从里到外环绕的矩阵,就像蛇一样一圈圈盘旋,由此成为蛇形环绕矩阵, 如下图就是简单的从外向里包围蛇形环绕矩阵。
打印这种矩阵可以采用分治思想,即将问题分解成子问题求解,每次打印最外一圈,依次向里,直到结束为止。比如上述图中,最外一层依次从上往下(1 - 4),从左往右(5 - 8),从下往上(9 - 12),从右往左(13 - 16);每次向数组写入n-1个数,即每一圈写入 4 *(n-1)个数据; 然后让子规模实现下一层的操作,n = n - 2; 假设每一层开始的点都是左上角,即(0,0),(1,1),(2,2)...... 等,是从对角线开始的,所以每层的起始标志是(begin,begin),对于下一子层就是begin = begin + 1;
同时注意结束条件,即当 n = 1 时,说明矩阵是基数矩阵,最后一个元素赋值即结束,n = 0 时说明矩阵是偶数矩阵,即结束;
C++源代码(使用循环和递归两种方式):
#include<bits/stdc++.h> //集成大部分头文件
using namespace std;
int N[20][20];
void write(int& i, int& k, int &n, int &num) { //蛇形写入数据,数据都为引用,为了不影响原操作
for(int j=1; j<n; j++) { //从上往下写入
N[i][k] = ++num;
i++;
}
for(int j=1; j<n; j++) { //从左往右写入
N[i][k] = ++num;
k++;
}
for(int j=1; j<n; j++) { //从下往上写入
N[i][k] = ++num;
i--;
}
for(int j=1; j<n; j++) { //从右往左写入
N[i][k] = ++num;
k--;
}
}
void show(int n) { //打印矩阵
for(int i=0; i<n; i++) {
for(int k=0; k<n; k++) {
printf("%4d ", N[i][k]);
}
cout<< endl<< endl;;
}
}
void snakeMatrix1(int n) { //使用循环实现蛇形矩阵
int begin = 0, num = 0, temp = n;
while(n > 0) {
int i, k;
i = k = begin;
if(n == 1) {
N[i][k] = ++num;
break;
}
write(i, k, n, num);
n -= 2;
begin ++;
}
printf("\n使用循环打印%d阶蛇形矩阵: \n", temp);
show(temp);
}
void snakeM(int n, int begin, int num) { //n:子规模大小,begin:子规模开始,num:计数
int i, k;
i = k = begin;
if(n == 1) { //基数矩阵判断条件,最后一项结束就return
N[i][k] = ++num;
return;
}
if(n == 0) { //偶数矩阵递归返回判断条件
return;
}
write(i, k, n, num);
snakeM(n-2, begin+1,num); //带入递归
}
void snakeMatrix2(int n) { //使用递归实现蛇形矩阵
memset(N, 0, sizeof(N)); //数组置位 (数组名称,指定变更,变更大小)
snakeM(n, 0, 0);
printf("使用递归打印%d阶蛇形矩阵: \n", n);
show(n);
}
void solve() {
int num = 0;
cout<< "请输入蛇形矩阵的规模: ";
cin>> num;
snakeMatrix1(num);
snakeMatrix2(num);
}
int main() {
solve();
return 0;
}