剑指offer 29. 顺时针打印矩阵
题目描述
解题思路
对于每层,从左上方开始以顺时针的顺序遍历所有元素,遍历完当前层的元素之后,将 left 和 top 分别增加 1,将 right 和 bottom 分别减少 1,进入下一层继续遍历,直到遍历完所有元素为止。
注意有个坑!
由于循环条件是 while (left <= right && top <= bottom)
,所以如果当前层仅有一列(left == right)或仅有一行(top == bottom),则只需打印上边界和右边界,否则会出现重复打印 。
class Solution {
public int[] res;
public int[] spiralOrder(int[][] matrix) {
if (matrix == null || matrix.length == 0 || matrix[0].length == 0) return new int[0];
//每一层的上下左右四个边界,从最外层开始
int top = 0, bottom = matrix.length - 1, left = 0, right = matrix[0].length - 1;
int[] res = new int[matrix.length * matrix[0].length];
int idx = 0; //res数组的指针
while (left <= right && top <= bottom) {
//上边界:(top, left) ~ (top, right)
for (int i = left; i <= right; i++) res[idx++] = matrix[top][i];
//右边界:(top + 1, right) ~ (bottom, right)
for (int i = top + 1; i <= bottom; i++) res[idx++] = matrix[i][right];
//注意!如果该层仅有一列或仅有一行,则只需打印上边界和右边界,否则会出现重复打印
if(left == right || top == bottom) break;
//下边界:(bottom, right - 1) ~ (bottom, left)
for (int i = right - 1; i >= left; i--) res[idx++] = matrix[bottom][i];
//左边界:(bottom - 1, left) ~ (top + 1, left)
for (int i = bottom - 1; i >= top + 1; i--) res[idx++] = matrix[i][left];
//进入下一层
left++; right--; top++; bottom--;
}
return res;
}
}