题目
给定一个正整数 n,生成一个包含 1 到 n2 所有元素,且元素按顺时针顺序螺旋排列的正方形矩阵。
示例:
输入: 3 输出: [ [ 1, 2, 3 ], [ 8, 9, 4 ], [ 7, 6, 5 ] ]
方法一:设定边界模拟法
要点:
1、循环的顺序一定要清晰且不变,比如这道题就是按照 左到右,上到下,右到左,下到上的顺序一直循环,向内缩进。
2、写的时候要认真,注意缩进时不变量是哪个(比如从左到右,matrix[i][top],第二维的top是不变的)
3、学习一下创建并分配二维vector空间的写法。
4、for循环不写花括号时, 后面跟着那行记得多空几下,不然报错(迷惑)for(int i=left;i<=right;i++) matrix[top][i] =num++;
class Solution {
public:
vector<vector<int>> generateMatrix(int n) {
// 创建二维矩阵,分配空间并创造对象
vector<vector<int>> matrix(n, vector<int>(n,0));
//另一种循环创建写法
vector<vector<int>> matrix(n);
for(int i=0;i<matrix.size();i++){
matrix[i].resize(n);
}
//设置左右上下四个边界
int left = 0;
int right =n-1;
int top =0;
int bottom =n-1;
int num =1;
while(num <=n*n){
for(int i=left;i<=right;i++) {
matrix[top][i] =num++;
}
top++; //上边界向下收缩一行
for(int i=top;i<=bottom;i++){
matrix[i][right] =num++;
}
right--; //右边界向内收缩一行
for(int i=right;i>=left;i--) {
matrix[bottom][i] =num++;
}
bottom--; //下边界向上收缩一行
for(int i=bottom;i>=top;i--){
matrix[i][left] =num++;
}
left++; //左边界向内收缩一行
}
return matrix;
}
};
JS
第一种还是我自己的那种写法,转一边就缩进一次
第二种是大佬写法,按照圈数来循环
PS:在做mxn的螺旋矩阵时,我发现我的这种while判断会有问题,并不能够在到达数组末尾后立刻退出,导致重复添加
var generateMatrix = function(n) {
let result =new Array(n).fill().map(()=>new Array(n))
let left =0
let right =n -1
let top =0
let bottom =n-1
let num =1
//我这个是左闭右闭
while(num<=n*n){
for(let i=left;i<=right;i++){
result[top][i] =num++
}
top++//上边界向下收缩一行
for(let i=top;i<=bottom;i++){
result[i][right] =num++
}
right--//右边界向内收缩一行
for(let i=right;i>=left;i--){
result[bottom][i] =num++
}
bottom--//下边界向上收缩一行
for(let i=bottom;i>=top;i--){
result[i][left] =num++
}
left++//左边界向内收缩一行
}
return result
};
var generateMatrix = function(n) {
let startX = startY = 0; // 起始位置
let loop = Math.floor(n/2); // 旋转圈数
let mid = Math.floor(n/2); // 中间位置
let offset = 1; // 控制每一层填充元素个数
let count = 1; // 更新填充数字
let res = new Array(n).fill(0).map(() => new Array(n).fill(0));
while (loop--) {
let row = startX, col = startY;
// 上行从左到右(左闭右开)
for (; col < startY + n - offset; col++) {
res[row][col] = count++;
}
// 右列从上到下(左闭右开)
for (; row < startX + n - offset; row++) {
res[row][col] = count++;
}
// 下行从右到左(左闭右开)
for (; col > startY; col--) {
res[row][col] = count++;
}
// 左列做下到上(左闭右开)
for (; row > startX; row--) {
res[row][col] = count++;
}
// 更新起始位置
startX++;
startY++;
// 更新offset
offset += 2;
}
// 如果n为奇数的话,需要单独给矩阵最中间的位置赋值
if (n % 2 === 1) {
res[mid][mid] = count;