螺旋矩阵(顺时针遍历矩阵)

leetcode 54.螺旋矩阵 

给你一个 m 行 n 列的矩阵 matrix ,请按照 顺时针螺旋顺序 ,返回矩阵中的所有元素。

和剑指office29题相似;

思路:既然是顺时针遍历一圈,那么我们就分别从上边,右边,下边,左边依次遍历,一圈完后在遍历下一圈,直到符合终止条件,停止循环,过程中将遍历到的值存入集合中,返回集合即可;

大体的思路如上所示,是很简单的,但是这个题的难点在于:

1.保证边界的取值是正确的,不会出现数组越界

2.我们需要保持每次遍历时的左闭右开还是左开右闭是统一的

3.终止条件的判断,什么时候算是全部遍历完成了

首先我们需要先定义四个变量,分别是上右下左,它们分别代表遍历的当前这个圈的上右下左四个边所处的位置,每遍历一次,就对应的缩小一个位置(这里可以实现左开右闭或者左闭右开),直到我们左和右相遇,或者上和下相遇,这是就意味着每个数已经遍历完成,就是终止条件。

综上,代码如下:

public List<Integer> spiralOrder(int[][] matrix) {
    List<Integer> lists = new ArrayList<>();
    int m = matrix.length ;//定义行数
    int n = matrix[0].length ;//定义列数
    //上下左右
    //注意,这里的上下左右四个值,分别指的是遍历这一行或者这一列时,保持不动的那个行数或列数
    //例如我们遍历第一行时,行数是up保持不变,列数是i进行递增
    int up = 0;//遍历时的点坐标[up,i]
    int right = n-1;//[i,right]
    int down = m-1;//[down,i]
    int left = 0;//[i,left]

    while (true){
        //从左到右
        for (int i = left; i <= right; i++) {lists.add(matrix[up][i]);}
        if (++up>down){break;}//每一行或者一列遍历完后,都要缩圈,这里是上边向下缩圈
        //up已经完成加1操作,向下移动了一行,因为下面的从上到下遍历,是从up这一行开始的
        //所以就实现了我们的右闭,后面的以此类推;
        //当移动后的up与down冲突时,意味着遍历已经结束了,break跳出循环,下面的同理。

        //从上到下
        for (int i = up; i <= down; i++) {lists.add(matrix[i][right]);}
        if (--right<left){break;}//右边遍历完,向左缩圈

        //从右到左
        for (int i = right; i >= left; i--) {lists.add(matrix[down][i]);}
        if (--down<up){break;}//下边遍历完,向上缩圈

        //从下到上
        for (int i = down; i >= up; i--) {lists.add(matrix[i][left]);}
        if (++left>right){break;}//左边遍历完,向右缩圈
    }
    return lists;
}

猜你喜欢

转载自blog.csdn.net/weixin_52394141/article/details/131310335