题目
https://leetcode-cn.com/problems/shun-shi-zhen-da-yin-ju-zhen-lcof/submissions/
题目:输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字。例如:如果输入如下矩阵:
思路
接下来分析循环结束的条件。假设这个矩阵的行数是 rows,列数是columns。打印第一圈的左上角的坐标是(1,1),第二圈的左上角的坐标是(2, 2),依此类推。我们注意到,左上角的坐标中行标和列标总是相同的,于是可以在矩阵中选取左上角为(start,start)的一圈作为我们分析的目标。
对一个5×5的矩阵而言,最后一圈只有一个数字,对应的坐标为(2,2)。我们发现5>2×2。对一个6×6的矩阵而言,最后一圈有4个数字,其左上角的坐标仍然为(2,2)。我们发现6>2×2依然成立。于是我们可以得出,让循环继续的条件是columns>startX ×2 并且rows>startY×2。
仔细分析每一步打印的前提条件,这个是重点。
代码
class Solution:
def spiralOrder(self, matrix: List[List[int]]) -> List[int]:
if not matrix:
return matrix
row, col = len(matrix), len(matrix[0])
i, j = 0, 0
def printCircle(start, matrix, rowBoundary=row, colBoundary=col):
ans = []
# left to right,总是需要从左打印
for j in range(start, colBoundary):
ans.append(matrix[start][j])
# up to down, 至少需要两行,才需要执行从上到下打印
if rowBoundary - start > 1:
for i in range(start+1, rowBoundary):
ans.append(matrix[i][colBoundary-1])
# right to left,至少需要两行两列
if rowBoundary - start > 1 and colBoundary - start > 1:
for j in range(colBoundary - 2, start-1, -1):
ans.append(matrix[rowBoundary-1][j])
# down to up,至少需要三行两列
if rowBoundary - start > 2 and colBoundary - start > 1:
for i in range(rowBoundary-2, start, -1):
ans.append(matrix[i][start])
return ans
start = 0
row, col = len(matrix), len(matrix[0])
result = []
while row > start * 2 and col > start * 2:
# print a loop
circleNums = printCircle(start, matrix, rowBoundary=row-start, colBoundary=col-start)
result.extend(circleNums)
start += 1
return result