📑 题目:54. 螺旋矩阵

🚀 本题 LeetCode 传送门

题目大意

给定一个包含 m x n 个元素的矩阵(m 行, n 列),请按照顺时针螺旋顺序,返回矩阵中的所有元素。

解题思路

  • 给出一个二维数组,按照螺旋的方式输出
  • 解法一:需要注意的是特殊情况,比如二维数组退化成一维或者一列或者一个元素。注意了这些情况,基本就可以一次通过了。
  • 解法二:提前算出一共多少个元素,一圈一圈地遍历矩阵,停止条件就是遍历了所有元素(count == sum)

代码

  1. package leetcode
  2. // 解法 1
  3. func spiralOrder(matrix [][]int) []int {
  4. if len(matrix) == 0 {
  5. return []int{}
  6. }
  7. res := []int{}
  8. if len(matrix) == 1 {
  9. for i := 0; i < len(matrix[0]); i++ {
  10. res = append(res, matrix[0][i])
  11. }
  12. return res
  13. }
  14. if len(matrix[0]) == 1 {
  15. for i := 0; i < len(matrix); i++ {
  16. res = append(res, matrix[i][0])
  17. }
  18. return res
  19. }
  20. visit, m, n, round, x, y, spDir := make([][]int, len(matrix)), len(matrix), len(matrix[0]), 0, 0, 0, [][]int{
  21. []int{0, 1}, // 朝右
  22. []int{1, 0}, // 朝下
  23. []int{0, -1}, // 朝左
  24. []int{-1, 0}, // 朝上
  25. }
  26. for i := 0; i < m; i++ {
  27. visit[i] = make([]int, n)
  28. }
  29. visit[x][y] = 1
  30. res = append(res, matrix[x][y])
  31. for i := 0; i < m*n; i++ {
  32. x += spDir[round%4][0]
  33. y += spDir[round%4][1]
  34. if (x == 0 && y == n-1) || (x == m-1 && y == n-1) || (y == 0 && x == m-1) {
  35. round++
  36. }
  37. if x > m-1 || y > n-1 || x < 0 || y < 0 {
  38. return res
  39. }
  40. if visit[x][y] == 0 {
  41. visit[x][y] = 1
  42. res = append(res, matrix[x][y])
  43. }
  44. switch round % 4 {
  45. case 0:
  46. if y+1 <= n-1 && visit[x][y+1] == 1 {
  47. round++
  48. continue
  49. }
  50. case 1:
  51. if x+1 <= m-1 && visit[x+1][y] == 1 {
  52. round++
  53. continue
  54. }
  55. case 2:
  56. if y-1 >= 0 && visit[x][y-1] == 1 {
  57. round++
  58. continue
  59. }
  60. case 3:
  61. if x-1 >= 0 && visit[x-1][y] == 1 {
  62. round++
  63. continue
  64. }
  65. }
  66. }
  67. return res
  68. }
  69. // 解法 2
  70. func spiralOrder2(matrix [][]int) []int {
  71. m := len(matrix)
  72. if m == 0 {
  73. return nil
  74. }
  75. n := len(matrix[0])
  76. if n == 0 {
  77. return nil
  78. }
  79. // top、left、right、bottom 分别是剩余区域的上、左、右、下的下标
  80. top, left, bottom, right := 0, 0, m-1, n-1
  81. count, sum := 0, m*n
  82. res := []int{}
  83. // 外层循环每次遍历一圈
  84. for count < sum {
  85. i, j := top, left
  86. for j <= right && count < sum {
  87. res = append(res, matrix[i][j])
  88. count++
  89. j++
  90. }
  91. i, j = top + 1, right
  92. for i <= bottom && count < sum {
  93. res = append(res, matrix[i][j])
  94. count++
  95. i++
  96. }
  97. i, j = bottom, right - 1
  98. for j >= left && count < sum {
  99. res = append(res, matrix[i][j])
  100. count++
  101. j--
  102. }
  103. i, j = bottom - 1, left
  104. for i > top && count < sum {
  105. res = append(res, matrix[i][j])
  106. count++
  107. i--
  108. }
  109. // 进入到下一层
  110. top, left, bottom, right = top+1, left+1, bottom-1, right-1
  111. }
  112. return res
  113. }