刷完LeetCode题库——498. 对角线遍历

137 阅读2分钟

持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第19天,点击查看活动详情

题目详情

LeetCode题库序号 498. 对角线遍历 ,难度为 中等

Tag : 「模拟」

给你一个大小为 m x n 的矩阵 mat,请以对角线遍历的顺序,用一个数组返回这个矩阵中的所有元素。

示例 1:

image.png

输入:mat = [[1,2,3],[4,5,6],[7,8,9]]
输出:[1,2,4,7,5,3,6,8,9]

示例 2:

输入:mat = [[1,2],[3,4]]
输出:[1,2,3,4]

提示:

  • m==mat.lengthm == mat.length
  • n==mat[i].lengthn == mat[i].length
  • 1<=m,n<=1041 <= m, n <= 10^4
  • 1<=m×n<=1041 <= m \times n <= 10^4
  • 105<=mat[i][j]<=105-10^5 <= mat[i][j] <= 10^5

进行模拟

首先我们需要把这个问题拆解成几个部分小问题的形式:

  • 第一个就是计算出矩形有多少条对象线,我们可以根据 m + n - 1 得出对角线的梳理。
  • 第二个就是根据对角线的方向,有从下往下,从上往下两个方向,根据i % 2 == 0,如果是偶数的话,对角线就是从下往上;如果是奇数的话,对角线就是从上往下。
  • 第三个根据对角线的方向,确定起点位置,可以想象很宽的距形。从下往上的起点位置的y点肯定会大于m的长度的。所以前面部分可以直接确定i,但是后面越来越大后,则需要根据找规律去计算公式。
  • 确定起点后,剩下的遍历就是最简单的部分了。只需要判断好边界值就可以了。

题解代码

class Solution {
   public int[] findDiagonalOrder(int[][] mat) {
        // 行数
        int m = mat.length;
        // 列数
        int n = mat[0].length;
        int[] ans = new int[m * n];
        int pos = 0;
        for(int i = 0; i < m + n - 1; i++) {
            if (i % 2 == 0) {
                // 从下往上
                int x = i < m ? i : m - 1;
                int y = i < m ? 0 : i - m + 1;
                while(x >= 0 && y < n) {
                    ans[pos] = mat[x][y];
                    x--;
                    y++;
                    pos++;
                }
            } else {
                // 从上往下
                int x = i < n ? 0 : i - n + 1;
                int y = i < n ? i : n - 1;
                while(x < m && y >= 0) {
                    ans[pos] = mat[x][y];
                    x++;
                    y--;
                    pos++;
                }
            }
        }

        return ans;
    }
}

结尾

我的"刷完LeetCode题库"系列文章的第 No.498 序号的题目,本次刷题之旅系列开始于 2022-06-12,因为LeetCode上部分是有锁题,我自己的目标是将先把所有不带锁的题目刷完。自己能够通过这次刷题之旅勉励自己,并且提升逻辑思维能力。这个系列的文章就是会见证我自己的一个成长过程!

思路虽然不是最优的,但是我会尽我所能!

为了让我自己的刷题之旅不中断,我特地建立了相关的仓库,来记录我自己的刷题之旅。 github.com/jackpan123/…