LeetCode刷题 day4

目录

1.至少是其他数字两倍的最大数

给你一个整数数组 nums ,其中总是存在 唯一的 一个最大整数 。

请你找出数组中的最大元素并检查它是否 至少是数组中每个其他数字的两倍 。如果是,则返回 最大元素的下标 ,否则返回 -1 。
示例 1:

输入:nums = [3,6,1,0]

输出:1

解释:6 是最大的整数,对于数组中的其他整数,6 至少是数组中其他元素的两倍。6 的下标是 1 ,所以返回 1 。
思路

只要找到最大数和第二大数即可,只要最大数比第二大数大两倍即可

java 复制代码
class Solution {
    public int dominantIndex(int[] nums) {
        int fMax=0,sMax=0;
        int fIndex=0;
        for(int i=0;i<nums.length;i++){
            if(nums[i]>fMax){
                sMax = fMax;
                fMax = nums[i];
                fIndex = i;
            }else if(nums[i]>sMax){
                sMax = nums[i];
            }
        }
        return fMax>=sMax*2?fIndex:-1;
    }
}

时间复杂度: O(N)
空间复杂度: O(1)

2.二进制表示中质数个计算置位

给你两个整数 left 和 right ,在闭区间 [left, right] 范围内,统计并返回 计算置位位数为质数 的整数个数。

计算置位位数 就是二进制表示中 1 的个数。

例如, 21 的二进制表示 10101 有 3 个计算置位。
示例 1:

输入:left = 6, right = 10

输出:4

解释:

6 -> 110 (2 个计算置位,2 是质数)

7 -> 111 (3 个计算置位,3 是质数)

9 -> 1001 (2 个计算置位,2 是质数)

10-> 1010 (2 个计算置位,2 是质数)

共计 4 个计算置位为质数的数字。
提示:
1 <= left <= right <= 10^6
0 <= right - left <= 10^4

思路

这里提示指出数字范围在10^6以内,二进制中1的个数2,3,5,7,11,13,17,19这些个数为质数,因此可以用32位的有符号数来标记这些数,将这些位置置为1,则得到32位有符号数665772,只要与该数按位与不为零,则表示为质数,统计即可

java 复制代码
class Solution {
	//数字n用二进制第n位为1来标记,相当于32位的bitmap
    //0000_0000_0000_0101_0001_0100_0101_0110=665772
    //2对应0010
    //3对应0100
    //5对应0001_0000
    //以此类推19对应0100_0000_0000_0000_0000,二进制第19位为1
    public int countPrimeSetBits(int left, int right) {
        int count = 0;
        int mask = 665772;
        while(left<=right){
            int n = left;
            int cnts = 0;
            //每循环一次,消除最右侧的1
            //复习位运算:x&(-x) lowBit运算,找到最低位的1 
            while(n>0){
            	//位运算:消除最低位的1
                n&=(n-1);
                cnts++;
            }
            if(((1<<cnts)&mask)!=0){
                count++;
            }
            left++;
        }
        return count;
    }
    
}

时间复杂度: O(right-left)
空间复杂度: O(1)

3. 托普利茨矩阵

给你一个 m x n 的矩阵 matrix 。如果这个矩阵是托普利茨矩阵,返回 true ;否则,返回 false 。

如果矩阵上每一条由左上到右下的对角线上的元素都相同,那么这个矩阵是托普利茨矩阵 。
示例 1:

输入:matrix = [[1,2,3,4],[5,1,2,3],[9,5,1,2]]

输出:true

解释:

在上述矩阵中, 其对角线为:

"[9]", "[5, 5]", "[1, 1, 1]", "[2, 2, 2]", "[3, 3]", "[4]"。

各条对角线上的所有元素均相同, 因此答案是True 。
思路

开始的思路是验证首行和首列,后来查看题解发现小技巧是,每次验证相邻行即可

java 复制代码
class Solution {
    public boolean isToeplitzMatrix(int[][] matrix) {
        int m=matrix.length,n=matrix[0].length;
        for(int i=0;i<m-1;i++){
            for(int j=0;j<n-1;j++){
                if(matrix[i][j]!=matrix[i+1][j+1]){
                    return false;
                }
            }
        }
        return true;
    }
}

时间复杂度: O(n*m) 遍历矩阵即可
空间复杂度: O(1)

4. 宝石与石头

给你一个字符串 jewels 代表石头中宝石的类型,另有一个字符串 stones 代表你拥有的石头。 stones 中每个字符代表了一种你拥有的石头的类型,你想知道你拥有的石头中有多少是宝石。

字母区分大小写,因此 "a" 和 "A" 是不同类型的石头。

示例 1:

输入:jewels = "aA", stones = "aAAbbbb"

输出:3

示例 2:

输入:jewels = "z", stones = "ZZ"

输出:0

思路

分别统计a-zA-Z是否为宝石,有一种bitmap的思路是用64位long型来标记a-zA-Z,大写字母二进制的低 6 位是从 000001 开始的(对应大写字母 A),一直到 011010(对应大写字母 Z)。

小写字母二进制的低 6 位是从 100001 开始的(对应小写字母 a),一直到 111010(对应小写字母 z),即十进制的 58。因此可以用低6位来区分大小写,每个数字对应一个字母

java 复制代码
class Solution {
    public int numJewelsInStones(String jewels, String stones) {
        long mask = 0;
        for(char c:jewels.toCharArray()){
        	//将字符与63与得到字符低6位对应的数字,将64位二进制数对应位置置为1
            mask |= 1L<<(c&63);
        }
        int cnt = 0;
        for(char c:stones.toCharArray()){
        	//判断该字符对应mask位置是否为1,为1则是宝石
            if((mask&(1L<<(c&63)))!=0){
                cnt++;
            }
        }
        return cnt;
    }
}

时间复杂度: O(m+n),m和n分别为两字符串长度
空间复杂度: O(1)

5. 网格图中机器人回家的最小代价

给你一个 m x n 的网格图,其中 (0, 0) 是最左上角的格子,(m - 1, n - 1) 是最右下角的格子。给你一个整数数组 startPos ,startPos = [startrow, startcol] 表示 初始 有一个 机器人 在格子 (startrow, startcol) 处。同时给你一个整数数组 homePos ,homePos = [homerow, homecol] 表示机器人的 家 在格子 (homerow, homecol) 处。

机器人需要回家。每一步它可以往四个方向移动:上,下,左,右,同时机器人不能移出边界。每一步移动都有一定代价。再给你两个下标从 0 开始的额整数数组:长度为 m 的数组 rowCosts 和长度为 n 的数组 colCosts 。

如果机器人往 上 或者往 下 移动到第 r 行 的格子,那么代价为 rowCosts[r] 。

如果机器人往 左 或者往 右 移动到第 c 列 的格子,那么代价为 colCosts[c] 。

请你返回机器人回家需要的 最小总代价 。
示例 1:

输入:startPos = [1, 0], homePos = [2, 3], rowCosts = [5, 4, 3], colCosts = [8, 2, 6, 7]

输出:18

解释:一个最优路径为:

从 (1, 0) 开始

-> 往下走到 (2, 0) 。代价为 rowCosts[2] = 3 。

-> 往右走到 (2, 1) 。代价为 colCosts[1] = 2 。

-> 往右走到 (2, 2) 。代价为 colCosts[2] = 6 。

-> 往右走到 (2, 3) 。代价为 colCosts[3] = 7 。

总代价为 3 + 2 + 6 + 7 = 18
思路

只要移动两点间的行差和列差即可

java 复制代码
class Solution {
    public int minCost(int[] startPos, int[] homePos, int[] rowCosts, int[] colCosts) {
        //若在家,代价为0
        if(startPos[0]==homePos[0]&&startPos[1]==homePos[1]){
            return 0;
        }
        int i = startPos[0]<=homePos[0]?1:-1;
        int j = startPos[1]<=homePos[1]?1:-1;
        int x = startPos[0];
        int y = startPos[1];
        int exp = 0;
        while(x!=homePos[0]){
            x+=i;
            exp += rowCosts[x];
        }
        while(y!=homePos[1]){
            y+=j;
            exp += colCosts[y];
        }
        return exp;
    }
}

时间复杂度: O(m+n) m和n分别是行数和列数
空间复杂度: O(1)

相关推荐
灵感__idea5 小时前
Hello 算法:“走一步看一步”的智慧
前端·javascript·算法
lwf0061647 小时前
导数学习日记
学习·算法·机器学习
头发够用的程序员8 小时前
从滑动窗口到矩阵运算:img2col算法基本原理
人工智能·算法·yolo·性能优化·矩阵·边缘计算·jetson
武帝为此8 小时前
【数据清洗缺失值处理】
python·算法·数学建模
Halo_tjn9 小时前
Java 基于字符串相关知识点
java·开发语言·算法
念越9 小时前
算法每日一题 Day08|双指针法解决三数之和
算法·力扣
黎阳之光9 小时前
黎阳之光透明管理:视频孪生重构智慧仓储新范式
人工智能·算法·安全·重构·数字孪生
6Hzlia10 小时前
【Hot 100 刷题计划】 LeetCode 199. 二叉树的右视图 | C++ DFS 逆序遍历
c++·leetcode·深度优先
CappuccinoRose10 小时前
回溯法 - 软考备战(四十三)
算法·排列组合·路径·n皇后·子集·解数独·岛屿
AC赳赳老秦10 小时前
OpenClaw进阶技巧:批量修改文件内容、替换关键词,解放双手
java·linux·人工智能·python·算法·测试用例·openclaw