@

283. 移动零

开始的想法是把零都挪到后面,看到了一种效率更高的写法,思路是先遍历一遍数组,把遇到的非零数按顺序重新复制,后面的全修改成零

public void moveZeroes(int[] nums) {
int idx = 0;
for (int num : nums) {
if (num != 0) {
nums[idx++] = num;
}
}
while (idx < nums.length) {
nums[idx++] = 0;
}
}

566. 重塑矩阵

遍历

class Solution {
public int[][] matrixReshape(int[][] nums, int r, int c) {
int m = nums.length, n = nums[0].length;
if (m * n != r * c) {
return nums;
}
int[][] reshapedNums = new int[r][c];
int index = 0;
for (int i = 0; i < r; i++) {
for (int j = 0; j < c; j++) {
reshapedNums[i][j] = nums[index / n][index % n];
index++;
}
}
return reshapedNums;
}
}

485. 最大连续1的个数

双指针法

class Solution {
public int findMaxConsecutiveOnes(int[] nums) {
int front = 0;
int last = 0;
int res = 0;
while (last < nums.length) {
if (nums[last] == 1) {
last ++;
}
/** 若出现0 保存当前最大连续值 重置指针*/
else {
res = Math.max(res, last - front);
front = last + 1;
last = front;
}
}
/** 判断最后的连续值是否是最大值 */
res = Math.max(res, last - front); return res;
}
}

240. 搜索二维矩阵 II

因为每一行递增,每一列递增。

所以本题的思路是从右上角往左下角找或者从左下角往右上角找。每次比较可以排除一行或者一列,时间复杂度为O(m+n)

和之前剑指offer上的一个题差不多

https://blog.csdn.net/hide_on_rush/article/details/105165885

class Solution {
public boolean searchMatrix(int[][] matrix, int target) {
if (matrix == null || matrix.length == 0 || matrix[0].length == 0) return false;
int m = matrix.length, n = matrix[0].length;
int row = 0, col = n - 1;
while (row < m && col >= 0) {
if (target == matrix[row][col]) return true;
else if (target < matrix[row][col]) col--;
else row++;
}
return false;
}
}

378. 有序矩阵中第K小的元素

二分查找法

public int kthSmallest(int[][] matrix, int k) {
int m = matrix.length, n = matrix[0].length;
int lo = matrix[0][0], hi = matrix[m - 1][n - 1];
while (lo <= hi) {
int mid = lo + (hi - lo) / 2;
int cnt = 0;
for (int i = 0; i < m; i++) {
for (int j = 0; j < n && matrix[i][j] <= mid; j++) {
cnt++;
}
}
if (cnt < k) lo = mid + 1;
else hi = mid - 1;
}
return lo;
}

645. 错误的集合

开始的想法是先排序,这种方法时间复杂度为 O(NlogN)。但是可以通过交换数组元素,使得数组上的元素在正确的位置上。这样的话时间复杂度为O(N),

空间复杂度为O(1)。

class Solution {
public int[] findErrorNums(int[] nums) {
for (int i = 0; i < nums.length; i++) {
while (nums[i] != i + 1 && nums[nums[i] - 1] != nums[i]) {
swap(nums, i, nums[i] - 1);
}
}
for (int i = 0; i < nums.length; i++) {
if (nums[i] != i + 1) {
return new int[]{nums[i], i + 1};
}
}
return null;
} private void swap(int[] nums, int i, int j) {
int tmp = nums[i];
nums[i] = nums[j];
nums[j] = tmp;
}
}

287. 寻找重复数

双指针解法要比二分法效率高

题解里找到的思路:

这里一共有n+1个元素,且元素的值为 [ 1 , n ],因此这里把下标i当做结点的标志,nums[ i ]当做是结点i的下一个结点的标志。这样从结点1到结点n中的任一个结点开始跳,必然会出现两种情况:

1.形成局部环(循环起始点不是初始点)

2.形成全局环(循环起始点是初始点)



情况1:如果是局部环,那么循环起始点的标志就是重复数字。

情况2:如果是全局环,则稍微复杂一点,因为它只能说明环内的结点所对应的值不重复,但整个全局环不一定包含所有结点。为了判断是否含有重复,还需要从剩下的点继续跳。

解决办法:由于情况2比较难处理(因为要判断剩余的结点是哪些),因此这里有一个小小的tips,我们不再是从结点1到结点n中任意位置起跳,而是从结点nums[ 0 ]起跳,这样即使形成的是全局环,循环的起点依然是重复数字(因为全局环意味着环内的末节点指向初始结点,而结点0又指向初始结点,因此,初始结点即循环起始点就是重复数字)。这样,无论情况1还是情况2,我们只需要找到循环起始点就可以了。

作者:shi-wen

链接:https://leetcode-cn.com/problems/find-the-duplicate-number/solution/kuai-man-zhi-zhen-de-yuan-li-0ms-100-by-shi-wen/

public int findDuplicate(int[] nums) {
int slow = nums[0], fast = nums[nums[0]];
while (slow != fast) {
slow = nums[slow];
fast = nums[nums[fast]];
}
fast = 0;
while (slow != fast) {
slow = nums[slow];
fast = nums[fast];
}
return slow;
}

667. 优美的排列 II

class Solution {
public int[] constructArray(int n, int k) {
int[] ret = new int[n];
ret[0] = 1;
for (int i = 1, interval = k; i <= k; i++, interval--) {
ret[i] = i % 2 == 1 ? ret[i - 1] + interval : ret[i - 1] - interval;
}
for (int i = k + 1; i < n; i++) {
ret[i] = i + 1;
}
return ret;
}
}

697. 数组的度

使用HashMap

class Solution {
public int findShortestSubArray(int[] nums) {
Map<Integer, Integer> numsCnt = new HashMap<>();
Map<Integer, Integer> numsLastIndex = new HashMap<>();
Map<Integer, Integer> numsFirstIndex = new HashMap<>();
for (int i = 0; i < nums.length; i++) {
int num = nums[i];
numsCnt.put(num, numsCnt.getOrDefault(num, 0) + 1);
numsLastIndex.put(num, i);
if (!numsFirstIndex.containsKey(num)) {
numsFirstIndex.put(num, i);
}
}
int maxCnt = 0;
for (int num : nums) {
maxCnt = Math.max(maxCnt, numsCnt.get(num));
}
int ret = nums.length;
for (int i = 0; i < nums.length; i++) {
int num = nums[i];
int cnt = numsCnt.get(num);
if (cnt != maxCnt) continue;
ret = Math.min(ret, numsLastIndex.get(num) - numsFirstIndex.get(num) + 1);
}
return ret;
}
}

766. 托普利茨矩阵

每个元素都跟左上角元素比较,因为第0行和第0列都没有左上角元素,所以两个索引都从1开始。

class Solution {
public boolean isToeplitzMatrix(int[][] matrix) {
for(int i = 1; i < matrix.length; i ++)
for(int j = 1; j < matrix[0].length; j ++)
if(matrix[i][j] != matrix[i-1][j-1])
return false;
return true;
}
}

565. 数组嵌套

将访问过的数标位-1,访问到-1直接跳出。原理是如果访问到之前一个循环中访问过的数,则说明也进入了之前的循环,没有必要再进行下去。

class Solution {
public int arrayNesting(int[] nums) {
int res = 0;
for(int i = 0; i < nums.length; i++){
int count = 0;
int k = i;
while(nums[k]!=-1){
int temp = k;
k = nums[k];
nums[temp] = -1;
count++;
}
res = Math.max(res,count);
}
return res; }
}

769. 最多能完成排序的块

class Solution {
public int maxChunksToSorted(int[] arr) {
if (arr == null) return 0;
int ret = 0;
int right = arr[0];
for (int i = 0; i < arr.length; i++) {
right = Math.max(right, arr[i]);
if (right == i) ret++;
}
return ret;
}
}

leetcode刷题记录——数组与矩阵的更多相关文章

  1. LeetCode刷题总结-数组篇(中)

    本文接着上一篇文章<LeetCode刷题总结-数组篇(上)>,继续讲第二个常考问题:矩阵问题. 矩阵也可以称为二维数组.在LeetCode相关习题中,作者总结发现主要考点有:矩阵元素的遍历 ...

  2. leetcode刷题记录--js

    leetcode刷题记录 两数之和 给定一个整数数组 nums 和一个目标值 target,请你在该数组中找出和为目标值的那 两个 整数,并返回他们的数组下标. 你可以假设每种输入只会对应一个答案.但 ...

  3. Leetcode刷题记录(python3)

    Leetcode刷题记录(python3) 顺序刷题 1~5 ---1.两数之和 ---2.两数相加 ---3. 无重复字符的最长子串 ---4.寻找两个有序数组的中位数 ---5.最长回文子串 6- ...

  4. LeetCode刷题总结-数组篇(上)

    数组是算法中最常用的一种数据结构,也是面试中最常考的考点.在LeetCode题库中,标记为数组类型的习题到目前为止,已累计到了202题.然而,这202道习题并不是每道题只标记为数组一个考点,大部分习题 ...

  5. LeetCode刷题总结-数组篇(下)

    本期讲O(n)类型问题,共14题.3道简单题,9道中等题,2道困难题.数组篇共归纳总结了50题,本篇是数组篇的最后一篇.其他三个篇章可参考: LeetCode刷题总结-数组篇(上),子数组问题(共17 ...

  6. LeetCode刷题记录(python3)

    由于之前对算法题接触不多,因此暂时只做easy和medium难度的题. 看完了<算法(第四版)>后重新开始刷LeetCode了,这次决定按topic来刷题,有一个大致的方向.有些题不止包含 ...

  7. leetcode 刷题记录(java)-持续更新

    最新更新时间 11:22:29 8. String to Integer (atoi) public static int myAtoi(String str) { // 1字符串非空判断 " ...

  8. LeetCode刷题 --杂篇 --数组,链表,栈,队列

    武汉加油,中国加油.希望疫情早日结束. 由于疫情,二狗寒假在家不能到处乱逛,索性就在家里系统的刷一下算法的内容,一段时间下来倒也有些小小的收获.只是一来家中的小破笔记本写起博客来实在不是很顺手,二来家 ...

  9. LeetCode 刷题记录(二)

    写在前面:因为要准备面试,开始了在[LeetCode]上刷题的历程.LeetCode上一共有大约150道题目,本文记录我在<http://oj.leetcode.com>上AC的所有题目, ...

随机推荐

  1. 如何从Python负零基础到精通数据分析

    一.为什么学习数据分析 1.运营的尴尬:运营人需要一个硬技能每个初入行的新人都会察觉到,运营是一个似乎并没有自己的核心竞争力和安全感的工作.因为每天的工作好像都被各种琐事所围绕,而只有一个主题是永恒不 ...

  2. 关于调用三方平台接口与推送接口的总结<二>(2020.7.27)

    前言:本篇博客是接着上篇总结写的,想了解怎么对接第三方平台接口的同学可以看我上一篇博客,地址是  https://www.cnblogs.com/alanturingson/p/13377500.ht ...

  3. Spring Cloud系列之使用Feign进行服务调用

    在上一章的学习中,我们知道了微服务的基本概念,知道怎么基于Ribbon+restTemplate的方式实现服务调用,接着上篇博客,我们学习怎么基于Feign实现服务调用,请先学习上篇博客,然后再学习本 ...

  4. Oracle 忘记密码 如何修改

    原文链接:https://jingyan.baidu.com/article/358570f6aaa1efce4724fcdf.html ️打开运行窗口 ️输入sqlplus "/ as s ...

  5. turtle库常用函数

  6. __name__=='__main__'作用

    .pyw:python源文件,常用语图形界面程序文件.pyc:Python字节码文件 举个例子吧!!先写一个py文件,命名为MyModule.py,里面内容如下: def mymain(): prin ...

  7. PHP 怎么安装

    您需要做什么? 为了开始使用 PHP,您可以: 找一个支持 PHP 和 MySQL 的 Web 主机 在您自己的 PC 机上安装 Web 服务器,然后安装 PHP 和 MySQL 使用支持 PHP 的 ...

  8. luogu P4775 [NOI2018]情报中心 线段树合并 虚树 树的直径trick

    LINK:情报中心 神题! 写了一下午 写到肚子疼. 调了一晚上 调到ex 用的是网上dalao的方法 跑的挺快的. 对于链的暴力 我不太会kk. 直接说正解吧: 分类讨论两种情况: 1 答案的两条链 ...

  9. luogu P6097 子集卷积 FST FWT

    LINK:子集卷积 学了1h多 终于看懂是怎么回事了(题解写的不太清楚 翻了好几篇博客才懂 一个需要用到的性质 二进制位为1个数是i的二进制数s 任意两个没有子集关系.挺显然. 而FST就是利用这个性 ...

  10. luogu P5892 [IOI2014]holiday 假期 决策单调性优化dp 主席树

    LINK:holiday 考虑第一个subtask. 容易想到n^2暴力枚举之后再暴力计算答案. 第二个subtask 暴力枚举终点可以利用主席树快速统计答案. 第三个subtask 暴力枚举两端利用 ...