leetcode(41-45)

19 篇文章 0 订阅

41. 缺失的第一个正数

给定一个未排序的整数数组,找出其中没有出现的最小的正整数。

示例 1:

输入: [1,2,0]
输出: 3

示例 2:

输入: [3,4,-1,1]
输出: 2

示例 3:

输入: [7,8,9,11,12]
输出: 1

说明:

你的算法的时间复杂度应为O(n),并且只能使用常数级别的空间。

class Solution {
public:
    int firstMissingPositive(vector<int>& nums) {
        for(int i=0;i<nums.size();){
            if(nums[i]>0 && nums[i]<=nums.size() && nums[i]!=nums[nums[i]-1]){
                swap(nums[i],nums[nums[i]-1]);
            } else {
                i++;
            }
        }
        for(int i=0;i<nums.size();i++){
            if(nums[i]!=i+1) return i+1;
        }
        return nums.size()+1;
    }
};

42. 接雨水

给定 n 个非负整数表示每个宽度为 1 的柱子的高度图,计算按此排列的柱子,下雨之后能接多少雨水。

上面是由数组 [0,1,0,2,1,0,1,3,2,1,2,1] 表示的高度图,在这种情况下,可以接 6 个单位的雨水(蓝色部分表示雨水)。 感谢 Marcos贡献此图。

示例:

输入: [0,1,0,2,1,0,1,3,2,1,2,1]
输出: 6
class Solution {
public:
    int trap(vector<int>& height) {
        int left=0,right=height.size()-1,lh=0,rh=0,res=0;
        while(left<right){
            if(height[left]<height[right]){
                if(height[left]<lh) res=res+lh-height[left];
                else lh=height[left];
                left++;
            } else {
                if(height[right]<rh) res=res+rh-height[right];
                else rh=height[right];
                right--;
            }
        }
        return res;
    }
};

43. 字符串相乘

给定两个以字符串形式表示的非负整数 num1 和 num2,返回 num1 和 num2 的乘积,它们的乘积也表示为字符串形式。

示例 1:

输入: num1 = "2", num2 = "3"
输出: "6"

示例 2:

输入: num1 = "123", num2 = "456"
输出: "56088"

说明:

  1. num1 和 num2 的长度小于110。
  2. num1 和 num2 只包含数字 0-9
  3. num1 和 num2 均不以零开头,除非是数字 0 本身。
  4. 不能使用任何标准库的大数类型(比如 BigInteger)直接将输入转换为整数来处理
class Solution {
public:
    string multiply(string num1, string num2) {
        const int m=num1.size();
        const int n=num2.size();
        vector<int> a(m+n,0);
        
        for(int i=0; i<m; i++){
            int dig=0;
            for(int j=0; j<n; j++){
                a[i+j] += (num1[m-1-i]-'0')*(num2[n-1-j]-'0')+dig;
                dig=a[i+j]/10;
                a[i+j] %= 10;
            }
            if(dig) a[n+i] += dig;
        }
        while(a.size()>1 && a.back()==0) a.pop_back();
        string res;
        for(auto it=a.rbegin();it!=a.rend();it++) res += *it+'0';
        return res;
    }
};

44. 通配符匹配

给定一个字符串 (s) 和一个字符模式 (p) ,实现一个支持 '?' 和 '*' 的通配符匹配。

'?' 可以匹配任何单个字符。
'*' 可以匹配任意字符串(包括空字符串)。

两个字符串完全匹配才算匹配成功。

说明:

  • s 可能为空,且只包含从 a-z 的小写字母。
  • p 可能为空,且只包含从 a-z 的小写字母,以及字符 ? 和 *

示例 1:

输入:
s = "aa"
p = "a"
输出: false
解释: "a" 无法匹配 "aa" 整个字符串。

示例 2:

输入:
s = "aa"
p = "*"
输出: true
解释: '*' 可以匹配任意字符串。

示例 3:

输入:
s = "cb"
p = "?a"
输出: false
解释: '?' 可以匹配 'c', 但第二个 'a' 无法匹配 'b'。

示例 4:

输入:
s = "adceb"
p = "*a*b"
输出: true
解释: 第一个 '*' 可以匹配空字符串, 第二个 '*' 可以匹配字符串 "dce".

示例 5:

输入:
s = "acdcb"
p = "a*c?b"
输入: false
class Solution {
public:
    bool isMatch(string s, string p) {
        int m=s.size(),n=p.size();
        vector<vector<int>> dp(m+1,vector<int>(n+1,0));
        dp[0][0]=1;
        for(int j=1; j<=n; j++) {
            if(p[j-1]=='*') dp[0][j]=dp[0][j-1];
        }
        for(int i=1; i<=m; i++){
            for(int j=1; j<=n; j++){
                if(p[j-1] != '*'){
                    if(p[j-1]==s[i-1] || p[j-1]=='?'){
                        dp[i][j]=dp[i-1][j-1];
                    }
                } else {
                        dp[i][j]=dp[i-1][j] || dp[i][j-1] || dp[i-1][j-1];
                    }
            }
        }
        return dp[m][n];
    }
};class Solution {
public:
    bool isMatch(string s, string p) {
        int m=s.size(),n=p.size();
        vector<vector<int>> dp(m+1,vector<int>(n+1,0));
        dp[0][0]=1;
        for(int j=1; j<=n; j++) {
            if(p[j-1]=='*') dp[0][j]=dp[0][j-1];
        }
        for(int i=1; i<=m; i++){
            for(int j=1; j<=n; j++){
                if(p[j-1] != '*'){
                    if(p[j-1]==s[i-1] || p[j-1]=='?'){
                        dp[i][j]=dp[i-1][j-1];
                    }
                } else {
                        dp[i][j]=dp[i-1][j] || dp[i][j-1] || dp[i-1][j-1];
                    }
            }
        }
        return dp[m][n];
    }
};

45. 跳跃游戏 II

给定一个非负整数数组,你最初位于数组的第一个位置。

数组中的每个元素代表你在该位置可以跳跃的最大长度。

你的目标是使用最少的跳跃次数到达数组的最后一个位置。

示例:

输入: [2,3,1,1,4]
输出: 2
解释: 跳到最后一个位置的最小跳跃数是 2。
     从下标为 0 跳到下标为 1 的位置,跳 1 步,然后跳 3 步到达数组的最后一个位置。

说明:

假设你总是可以到达数组的最后一个位置。

class Solution {
public:
    int jump(vector<int>& nums) {
        if(nums.size() <= 1) return 0;
        int index,max=0,step=0,i=0;
        while(i<nums.size()){
            if(i+nums[i] >= nums.size()-1){
                step++;
                break;
            }
            max=0;
            index=i+1;
            for(int j=i+1; j-i<=nums[i]; j++){
                if(max<nums[j]+j-i){
                    max=nums[j]+j-i;
                    index=j;
                }
            }
            i=index;
            step++;
        }
        return step;
    }
};

(以上题目均摘自leetcode)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值