之前研究螺旋矩阵,网上代码绕来绕去很迷惑,下面是一个简单易懂的版本,看完就能直接写出。
题目要求生成一个 n x n
的矩阵,这个矩阵的数字从 1
开始到 n^2
结束,数字按照从外到内顺时针螺旋的方式排列。简单来说,就是让你创建一个正方形的数字阵列,数字从中心向四周螺旋展开,直到填满整个矩阵。
让我们通过一个 4x4
的矩阵来详细解释题目,同时展示变量的变化和矩阵的更新过程。
初始状态
n = 4
- 初始矩阵
matrix = [[0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0]]
left = 0
,right = 3
top = 0
,down = 3
num = 1
迭代过程与矩阵更新
第一圈填充
- 填充顶行
top
从左到右 (left
到right
)matrix[0][0] = 1
,matrix[0][1] = 2
,matrix[0][2] = 3
,matrix[0][3] = 4
top++
->top = 1
- 填充右列
right
从上到下 (top
到down
)matrix[1][3] = 5
,matrix[2][3] = 6
,matrix[3][3] = 7
right--
->right = 2
- 填充底行
down
从右到左 (right
到left
)matrix[3][2] = 8
,matrix[3][1] = 9
,matrix[3][0] = 10
down--
->down = 2
- 填充左列
left
从下到上 (down
到top
)matrix[2][0] = 11
,matrix[1][0] = 12
left++
->left = 1
矩阵现在看起来是这样的:
1 2 3 4
12 0 0 5
11 0 0 6
10 9 8 7
第二圈填充
- 填充新的顶行
top
从左到右 (left
到right
)matrix[1][1] = 13
,matrix[1][2] = 14
top++
->top = 2
- 填充新的右列
right
从上到下 (top
到down
)matrix[2][2] = 15
right--
->right = 1
- 填充新的底行
down
从右到左 (right
到left
)matrix[2][1] = 16
down--
->down = 1
矩阵现在看起来是这样的:
1 2 3 4
12 13 14 5
11 16 15 6
10 9 8 7
由于 left > right
和 top > down
,循环结束,所有的 4x4
矩阵都已经正确填充。
变量变化概览
- 初始:
left = 0
,right = 3
,top = 0
,down = 3
,num = 1
- 第一圈结束后:
left = 1
,right = 2
,top = 1
,down = 2
- 第二圈结束后:
left = 2
,right = 1
,top = 2
,down = 1
(此时循环条件不再满足,循环结束) - 最终生成的矩阵:
1 2 3 4
12 13 14 5
11 16 15 6
10 9 8 7
结论
这段代码通过控制 left
、right
、top
、down
四个边界指针,在每一圈的迭代中逐步填充矩阵,最终生成一个按螺旋顺序填充数字的 4x4
矩阵。每完成一圈后,相应地调整这四个指针的值,直到填充完成。
代码
下面的代码挺容易理解的,直接模拟即可。
class Solution {
public:
vector<vector<int>> generateMatrix(int n) {
// 创建一个n*n的矩阵,初始值为0
vector<vector<int>> matrix(n, vector<int>(n , 0));
// 定义四个方向的边界:左、右、上、下
int left = 0 , right = n - 1;
int top = 0, down = n - 1;
// 初始数字从1开始
int num = 1;
// 当左边界不超过右边界,且上边界不超过下边界时,循环继续
while (left <= right && top <= down) {
// 从左到右填充上边界的行
for (int i = left; i <= right; i++) {
matrix[top][i] = num++; // 填充并将num递增
}
top++; // 上边界下移
// 从上到下填充右边界的列
for (int i = top; i <= down; i++) {
matrix[i][right] = num++; // 填充并将num递增
}
right--; // 右边界左移
// 从右到左填充下边界的行
for (int i = right; i >= left; i--) {
matrix[down][i] = num++; // 填充并将num递增
}
down--; // 下边界上移
// 从下到上填充左边界的列
for (int i = down; i >= top; i--) {
matrix[i][left] = num++; // 填充并将num递增
}
left++; // 左边界右移
}
// 返回填充完成的矩阵
return matrix;
}
};
此代码通过不断缩小矩阵的边界(左、右、上、下)来实现螺旋填充。每完成矩阵的一圈(即一层)的填充后,相应地调整边界条件,直到所有数字都被填充到矩阵中。这种方式有效地利用了螺旋路径的模式,确保了填充顺序的正确性和高效性。