• 博客园logo
  • 会员
  • 众包
  • 新闻
  • 博问
  • 闪存
  • 赞助商
  • HarmonyOS
  • Chat2DB
    • 搜索
      所有博客
    • 搜索
      当前博客
  • 写随笔 我的博客 短消息 简洁模式
    用户头像
    我的博客 我的园子 账号设置 会员中心 简洁模式 ... 退出登录
    注册 登录
haipali
博客园    首页    新随笔    联系   管理    订阅  订阅

算法 -- 和有限的最长子序列

  1. 和有限的最长子序列
    提示
    简单
    84
    相关企业
    给你一个长度为 n 的整数数组 nums ,和一个长度为 m 的整数数组 queries 。

返回一个长度为 m 的数组 answer ,其中 answer[i] 是 nums 中 元素之和小于等于 queries[i] 的 子序列 的 最大 长度 。

子序列 是由一个数组删除某些元素(也可以不删除)但不改变剩余元素顺序得到的一个数组。

示例 1:

输入:nums = [4,5,2,1], queries = [3,10,21]
输出:[2,3,4]
解释:queries 对应的 answer 如下:

  • 子序列 [2,1] 的和小于或等于 3 。可以证明满足题目要求的子序列的最大长度是 2 ,所以 answer[0] = 2 。
  • 子序列 [4,5,1] 的和小于或等于 10 。可以证明满足题目要求的子序列的最大长度是 3 ,所以 answer[1] = 3 。
  • 子序列 [4,5,2,1] 的和小于或等于 21 。可以证明满足题目要求的子序列的最大长度是 4 ,所以 answer[2] = 4 。
    示例 2:

输入:nums = [2,3,4,5], queries = [1]
输出:[0]
解释:空子序列是唯一一个满足元素和小于或等于 1 的子序列,所以 answer[0] = 0 。

提示:

n == nums.length
m == queries.length
1 <= n, m <= 1000
1 <= nums[i], queries[i] <= 106

解法:
排序+贪心+二分
由于数组顺序对结果没有影响,故先排序,而后要求和最小序列树,故将数相加,最后用二分法找小于等于target的数的最大值
上代码

class Solution {
    public int[] answerQueries(int[] nums, int[] queries) {
        int n = nums.length,m = queries.length;
        Arrays.sort(nums);
        int[] f = new int[n+1];
        for(int i=0;i<n;i++){
            f[i+1] = f[i]+nums[i];
        }
        int[] res = new int[m];
        for(int i=0;i<m;i++){
            res[i] = len(f,queries[i])-1;
        }
        return res;
    }
    private int len(int[] f,int target){
        int left = 1,right = f.length;
        while(left<right){
            int mid = left + (right-left)/2;
            if(f[mid]>target){
                right = mid;
            }else{
                left = mid+1;
            }
        }
        return left;
    }
}
posted @ 2023-03-17 17:07  蓝光水母  阅读(51)  评论(0)    收藏  举报
刷新页面返回顶部
博客园  ©  2004-2025
浙公网安备 33010602011771号 浙ICP备2021040463号-3