【解题报告】《LeetCode零基础指南》(第九讲) 二级指针 - Java

在这里插入图片描述

一、832. 翻转图像

1.题目

832. 翻转图像

给定一个二进制矩阵 A,我们想先水平翻转图像,然后反转图像并返回结果。
水平翻转图片就是将图片的每一行都进行翻转,即逆序。例如,水平翻转 [1, 1, 0] 的结果是 [0, 1, 1]。
反转图片的意思是图片中的 0 全部被 1 替换, 1 全部被 0 替换。例如,反转 [0, 1, 1] 的结果是 [1, 0, 0]。

2.分析

  • 这道题最直接的方法就是:先遍历一次二维数组,将数组每一行翻转,再遍历一次将0变1,1变0。
  • 优化后,代码把这两个过程合在一次遍历中:在数组元素进行交换的同时,对元素进行反转
    • 即:t = image[i][j];
    • image[i][j] = image[i][k] ^ 1
    • image[i][k] = t ^ 1

3.代码

class Solution {
    public int[][] flipAndInvertImage(int[][] image) {
        int i,j,k;
        for (i = 0;i < image.length;i++){
            j = 0;
            k = image[i].length - 1;
            while (j <= k){
                int t = image[i][j];
                image[i][j] = image[i][k] ^ 1;
                image[i][k] = t ^ 1;
                j++;
                k--;
            }
        }
        return image;
    }
}

在这里插入图片描述

二、867. 转置矩阵

1.题目

867. 转置矩阵

给你一个二维整数数组 matrix, 返回 matrix 的 转置矩阵 。
矩阵的 转置 是指将矩阵的主对角线翻转,交换矩阵的行索引与列索引。

2.分析

  • 转置矩阵从数组坐标的视角分析,就是坐标的值互换,即: ( 0 , 1 ) = > ( 1 , 0 ) (0,1) => (1,0) (0,1)=>(1,0)
  • 所以直接新建一个二维数组 int[][] res,新数组的数组长度与原数组的数组长度相反,即 r e s . l e n g t h = m a t r i x [ 0 ] . l e n g t h res.length=matrix[0].length res.length=matrix[0].length r e s [ 0 ] . l e n g t h = m a t r i x . l e n g t h res[0].length=matrix.length res[0].length=matrix.length
  • 再遍历原数组,将元素赋值到新数组中 r e s [ j ] [ i ] = m a t r i x [ i ] [ j ] res[j][i] = matrix[i][j] res[j][i]=matrix[i][j]

3.代码

class Solution {
    public int[][] transpose(int[][] matrix) {
        int m = matrix.length,n = matrix[0].length;
        int[][] res = new int[n][m];
        int i,j;
        for (i = 0;i < m;i++){
            for (j = 0;j < n;j++){
                res[j][i] = matrix[i][j];
            }
        }
        return res;
    }
}

在这里插入图片描述

三、566. 重塑矩阵

1.题目

566. 重塑矩阵

在 MATLAB 中,有一个非常有用的函数 reshape ,它可以将一个 m x n 矩阵重塑为另一个大小不同(r x c)的新矩阵,但保留其原始数据。
给你一个由二维数组 mat 表示的 m x n 矩阵,以及两个正整数 r 和 c ,分别表示想要的重构的矩阵的行数和列数。
重构后的矩阵需要将原始矩阵的所有元素以相同的 行遍历顺序 填充。
如果具有给定参数的 reshape 操作是可行且合理的,则输出新的重塑矩阵;否则,输出原始矩阵。

2.分析

  • 先判断原数组的元素个数跟给定条件 r ∗ c r * c rc 是否相同,不相同直接返回原数组。
  • 新建目标数组 i n t [ ] [ ] r e s = n e w i n t [ r ] [ c ] ; int[][] res = new int[r][c]; int[][]res=newint[r][c];
  • 遍历 [ 0 , r ∗ c ) [0,r*c) [0,rc),将原数组的值赋值到新数组,下标计算为:res[i / c][i % c] = mat[i / n][i % n];

3.代码

class Solution {
    public int[][] matrixReshape(int[][] mat, int r, int c) {
        int m = mat.length,n = mat[0].length;
        //总元素个数
        int counts = m * n;
        if (counts != r * c){
            return mat;
        }
        int[][] res = new int[r][c];
        int i;
        for (i = 0;i < counts;i++){
            res[i / c][i % c] = mat[i / n][i % n];
        }
        return res;
    }
}

在这里插入图片描述

四、2022. 将一维数组转变成二维数组

1.题目

2022. 将一维数组转变成二维数组

给你一个下标从 0 开始的一维整数数组 original 和两个整数 m 和 n 。你需要使用 original 中 所有 元素创建一个 m 行 n 列的二维数组。
original 中下标从 0 到 n - 1 (都 包含 )的元素构成二维数组的第一行,下标从 n 到 2 * n - 1 (都 包含 )的元素构成二维数组的第二行,依此类推。
请你根据上述过程返回一个 m x n 的二维数组。如果无法构成这样的二维数组,请你返回一个空的二维数组。

2.分析

  • 先判断一维数组元素个数是否等于给定二维数组的存储空间 m ∗ n m*n mn,不相等返回空的二维数组。
  • 遍历新建的二维数组,将一维数组的元素赋值到二维数组相应的位置。

3.代码

class Solution {
    public int[][] construct2DArray(int[] original, int m, int n) {
        if (original.length != m * n){
            return new int[][]{};
        }
        int[][] res = new int[m][n];
        int i,j,t = 0;
        for (i = 0;i < m;i++){
            for (j = 0;j < n;j++){
                res[i][j] = original[t++];
            }
        }
        return res;
    }
}

在这里插入图片描述

五、1260. 二维网格迁移

1.题目

1260. 二维网格迁移

给你一个 m 行 n 列的二维网格 grid 和一个整数 k。你需要将 grid 迁移 k 次。
每次「迁移」操作将会引发下述活动:
位于 grid[i][j] 的元素将会移动到 grid[i][j + 1]。
位于 grid[i][n - 1] 的元素将会移动到 grid[i + 1][0]。
位于 grid[m - 1][n - 1] 的元素将会移动到 grid[0][0]。
请你返回 k 次迁移操作后最终得到的 二维网格。

2.分析

  1. 定义一维数组,遍历的时候,将二维数组的元素赋值到一维数组迁移k步后的位置(迁移前:二维数组的 ( 0 , 0 ) (0,0) (0,0)对应一维数组的下标0位置)
  2. 一维数组长度为 :行数 * 列数( m ∗ n m * n mn)
  3. 防止 k 大于一维数组长度出现数组越界,当 k 大于等于一维数组长度,k需要再从下标0开始数:所以 k %= (行数 * 列数)
  4. 遍历一维数组存入集合List时,可以模仿遍历二维数组的方式,但取值是取一维数组的值

3.代码

class Solution {
    public List<List<Integer>> shiftGrid(int[][] grid, int k) {
        int a = 0;
        int m = grid.length;
        int n = grid[a].length;
        //把二维数组转换成一维数组
        int[] g = new int[m * n];
        for (int i = 0;i < m;i++){
            for (int j = 0;j < n;j++){
                //防止迁移大于 m * n步
                if (k >= g.length){
                    k %= g.length;
                }
                g[k] = grid[i][j];
                k++;
            }
        }
        //存到List集合
        List<Integer> list = null;
        List<List<Integer>> list2 = new ArrayList<>();
        for (int i = 0; i < m; i++) {
            list = new ArrayList<>();
            for (int j = 0; j < n; j++) {
                list.add(g[j + i * n]);
            }
            list2.add(list);
        }
        return list2;
    }
}

在这里插入图片描述

六、661. 图片平滑器

1.题目

661. 图片平滑器

包含整数的二维矩阵 M 表示一个图片的灰度。你需要设计一个平滑器来让每一个单元的灰度成为平均灰度 (向下舍入) ,平均灰度的计算是周围的8个单元和它本身的值求平均,如果周围的单元格不足八个,则尽可能多的利用它们。

2.分析

  • 我们以正中间的元素 ( i , j ) (i,j) (i,j)为例,它周围的8个元素相对于 ( i , j ) (i,j) (i,j) 的坐标偏移量如下图所示:
    在这里插入图片描述
  • 因此,我们可以先用两个数组分别记录下标 i 和 j i和j ij的偏移量,再在遍历元素的时候,加上偏移量来累加周围元素的值,进而求出当前遍历位置的平均灰度。
  1. 定义两个以为数组,分别记录某个元素周围8个位置的偏移量
  2. 新建二维数组,用于存储计算出来相应位置的平均灰度
  3. 遍历原二维数组 i n t [ ] [ ] i m g int[][] img int[][]img,同时遍历2个偏移量数组,若当前下标加上偏移量仍在矩阵内,则累加并计数。
  4. 全部周围的元素都累加完毕,则计算当前位置的平均灰度 s u m / c o u n t sum / count sum/count

3.代码

class Solution {
    public int[][] imageSmoother(int[][] img) {
        int m = img.length,n = img[0].length;
        //a表示下标i偏移量,b表示下标j偏移量
        int[] a = new int[]{-1,1,0,0,1,-1,1,-1};
        int[] b = new int[]{0,0,-1,1,1,1,-1,-1};
        //新数组存储计算后的值
        int[][] res = new int[m][n];
        for (int i = 0;i < m;i++){
            for (int j = 0;j < n;j++){
                //先累加自身
                int sum = img[i][j];
                //记录累加的元素个数
                int count = 1;
                //遍历周围的元素,进行累加
                for (int t = 0;t < a.length;t++){
                    int x = i + a[t],y = j + b[t];
                    //如果偏移后的坐标在矩阵内,累加并计数
                    if (x >= 0 && x < m && y >=0 && y < n){
                        sum += img[x][y];
                        count++;
                    }
                }
                //求当前位置的平均灰度
                res[i][j] = sum / count;
            }
        }
        return res;
    }
}

在这里插入图片描述

七、1314. 矩阵区域和

1.题目

1314. 矩阵区域和

给你一个 m x n 的矩阵 mat 和一个整数 k ,请你返回一个矩阵 answer ,其中每个 answer[i][j] 是所有满足下述条件的元素 mat[r][c] 的和:
i - k <= r <= i + k,
j - k <= c <= j + k 且
(r, c) 在矩阵内。

2.分析

3.代码

八、1030. 距离顺序排列矩阵单元格

1.题目

1030. 距离顺序排列矩阵单元格

给出 R 行 C 列的矩阵,其中的单元格的整数坐标为 (r, c),满足 0 <= r < R 且 0 <= c < C。
另外,我们在该矩阵中给出了一个坐标为 (r0, c0) 的单元格。
返回矩阵中的所有单元格的坐标,并按到 (r0, c0) 的距离从最小到最大的顺序排,其中,两单元格(r1, c1) 和 (r2, c2) 之间的距离是曼哈顿距离,|r1 - r2| + |c1 - c2|。(你可以按任何满足此条件的顺序返回答案。)

2.分析

3.代码

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
©️2022 CSDN 皮肤主题:数字20 设计师:CSDN官方博客 返回首页

打赏作者

小笼包95

你的鼓励将是我创作的最大动力

¥2 ¥4 ¥6 ¥10 ¥20
输入1-500的整数
余额支付 (余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值