【LeetCode 每日一题】2389. 和有限的最长子序列(easy)

2389. 和有限的最长子序列


暴力 O ( m n ) O(mn) O(mn)

由于是求符合条件的子序列的长度,所以我们其实不用考虑子序列的顺序问题。先计算一个前缀和,然后遍历 q u e r i e s queries queries ,枚举 n u m s nums nums 数组中的每一个位置。当 q u e r i e s [ i ] < n u m s [ j ] queries[i]<nums[j] queries[i]<nums[j] 时, j j j 即为符合条件的最大子序列长度 ,注意长度为n的情况

class Solution {
    
    
public:
    vector<int> answerQueries(vector<int>& nums, vector<int>& queries) {
    
    
        int n=nums.size();
        int m=queries.size();
        vector<int> res(m,n);//初始化为n
        sort(nums.begin(),nums.end());
        for(int i=1;i<n;i++) nums[i]+=nums[i-1];
        for(int i=0;i<m;i++){
    
    
            for(int j=0;j<n;j++){
    
    
                if(nums[j]>queries[i]) res[i]=min(j,res[i]);
            }
        }
        return res;
    }
};

在这里插入图片描述




二分优化 O ( ( n + m ) l o g n ) O((n+m)log^n) O((n+m)logn)

由于前缀和数组是有序的,用二分去查找不大于 q u e r i e s [ i ] queries[i] queries[i] 的数的位置会快很多。

class Solution {
    
    
public:
    vector<int> answerQueries(vector<int>& nums, vector<int>& queries) {
    
    
        sort(nums.begin(), nums.end());
        for (int i=1;i<nums.size();i++)
            nums[i]+=nums[i-1];
        for (int &q:queries)
            q=upper_bound(nums.begin(),nums.end(),q)-nums.begin();
        return queries;
    }
};

在这里插入图片描述




尝试继续优化失败

想了一下,能不能贪心贪到底呀。
q u e r i e s queries queries中每个数的位置用哈希表记一下,然后把 q u e r i e s queries queries 也排序,用双指针去做, O ( l o g n ) O(log^n) O(logn)就可以了。

class Solution {
    
    
public:
    vector<int> answerQueries(vector<int>& nums, vector<int>& queries) {
    
    
        int n=nums.size();
        int m=queries.size();
        vector<int> res(m,n);
        map<int,int> index;
        sort(nums.begin(),nums.end());
        for(int i=1;i<n;i++) nums[i]+=nums[i-1];
        for(int i=0;i<m;i++) index[queries[i]]=i;
        sort(queries.begin(),queries.end());
        int i=0,j=0;
        while(i<m&&j<n){
    
    
            if(nums[j]>queries[i]){
    
    
                int idx=index[queries[i]];//这个数在queries里面原本的位置
                res[idx]=min(j,res[idx]);
                i++;
            }
            else j++;
        }
        return res;
    }
};

提交之后老WA在第52组,力扣提供的答案对比也没爆红,可能是数组太长了。看了一圈题解,也没人用这个思路。
想了很久,才突然反应过来, q u e r i e s queries queries 里的元素并不是唯一的,会有哈希冲突。如果用不了哈希表,那就不存在比二分查找更优的办法了。






菩萨蛮【清·纳兰性德】

催花未歇花奴鼓,酒醒已见残红舞。不忍覆馀觞,临风泪数行。
粉香看又别,空剩当时月。月也异当时,凄清照鬓丝。

  1. 花奴:人名,唐玄宗时汝阳王李琎的小字。
  2. 残红舞:落花。
  3. 馀觞:杯中残留的酒。
  4. 粉香:代指爱妻或情有所终的女子。

猜你喜欢

转载自blog.csdn.net/qq_44623371/article/details/129617727