LeetCode 327. 区间和的个数(multiset二分查找/归并排序)

文章目录

    • 1. 题目
    • 2. 解题
      • 2.1 动态规划超时
      • 2.2 二分查找
      • 2.3 归并排序

1. 题目

给定一个整数数组 nums,返回区间和在 [lower, upper] 之间的个数,包含 lower 和 upper。

区间和 S(i, j) 表示在 nums 中,位置从 i 到 j 的元素之和,包含 i 和 j (i ≤ j)。

说明:
最直观的算法复杂度是 O(n2) ,请在此基础上优化你的算法。

示例:
输入: nums = [-2,5,-1], lower = -2, upper = 2,
输出: 3 
解释: 3个区间分别是: [0,0], [2,2], [0,2],它们表示的和分别为: -2, -1, 2

来源:力扣(LeetCode) 链接:https://leetcode-cn.com/problems/count-of-range-sum
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

2. 解题

2.1 动态规划超时

  • 区间动态规划,超时例子,复杂度太高 O(n2)O(n^2)O(n2)
  • 整型溢出例子[2147483647,-2147483648,-1,0] -1 0
    在这里插入图片描述
class Solution {
public:int countRangeSum(vector<int>& nums, int lower, int upper) {if(nums.size() == 0)return 0;int i, j, len, n = nums.size(), count=0;vector<vector<long>> dp(n,vector<long>(n,0));//区间[i,j]的和for(i = 0; i < n; ++i){dp[i][i] = nums[i];if(lower<=dp[i][i] && dp[i][i]<=upper)count++;}for(len = 1; len < n; ++len){for(i = 0; i < n-len; ++i){dp[i][i+len] = dp[i][i+len-1] + dp[i+len][i+len];if(lower<=dp[i][i+len] && dp[i][i+len]<=upper)count++;}}return count;}
};

2.2 二分查找

  • 参考大佬的解法
  • 前缀和 sum, L≤sum[j]−sum[i]≤U⇒sum[j]−U≤sum[i]≤sum[j]−LL \le sum[j]-sum[i] \le U \Rightarrow sum[j]-U\le sum[i] \le sum[j]-LLsum[j]sum[i]Usum[j]Usum[i]sum[j]L
  • j = 0 时, 上式 sum[i] = 0,sum[i] 可以看做前面的和, sum[j] 当前的和
  • 以每个 j 点作为结束的区间,前面哪些 i 到 j 的和在范围内
  • 将前次的前缀和插入multiset,有序,可以二分查找
  • 查找set中前缀值在 当前 前缀和 sum[j]sum[j]sum[j] 上下范围内([sum[j]−U,sum[j]−L][sum[j]-U, sum[j]-L][sum[j]U,sum[j]L])的个数
class Solution {
public:int countRangeSum(vector<int>& nums, int lower, int upper) {if(nums.size() == 0)return 0;multiset<long> s;s.insert(0);int count = 0;long sum = 0;for(int i = 0; i < nums.size(); ++i){sum += nums[i];count += distance(s.lower_bound(sum-upper), s.upper_bound(sum-lower));s.insert(sum);}return count;}
};

但是上面解法中distance在set中(不可随机访问)是 O(n)时间复杂度的,所以用数组进行二分查找两个端点,然后做差会更快些。
80 ms 14.4 MB

2.3 归并排序

  • 其实归并排序求逆序度是本题的一个特例
  • 对前缀和进行归并排序(注意头部要加一个0,用于第一个数的)
  • 归并时,固定左边的一个端点,右边有两个指针进行遍历查找

核心代码段:

		int i = l, jlo = mid+1, jup = mid+1;//右侧两个指针while(i <= mid)//遍历左侧的端点{	while(jlo <= r && sum[jlo]-sum[i] < lower)//[i,jlo]不在范围内jlo++;while(jup <= r && sum[jup]-sum[i] <= upper)//[i,jup]在范围内jup++;//最后 [jlo,jup) 为在范围内的右端点count += jup-jlo;//计数i++;//遍历下一个左端点}
class Solution {vector<long> temp;
public:int countRangeSum(vector<int>& nums, int lower, int upper) {if(nums.size() == 0)return 0;vector<long> sum(nums.size()+1, 0);temp.resize(nums.size()+1);for(int i = 1; i < sum.size(); ++i)sum[i] = sum[i-1] + nums[i-1];return mergeSort(sum,0,sum.size()-1,lower,upper);}int mergeSort(vector<long>& sum, int l, int r, int lower, int upper){if(l >= r)return 0;int mid = l+((r-l)>>1), count = 0;count += mergeSort(sum, l, mid, lower, upper);count += mergeSort(sum, mid+1, r, lower, upper);int i = l, jlo = mid+1, jup = mid+1;while(i <= mid){while(jlo <= r && sum[jlo]-sum[i] < lower)jlo++;while(jup <= r && sum[jup]-sum[i] <= upper)jup++;count += jup-jlo;i++;}//合并,跟归并排序一致i = l; int j = mid+1, k = 0;while(i <= mid && j <= r){if(sum[i] <= sum[j])temp[k++] = sum[i++];elsetemp[k++] = sum[j++];}if(i <= mid)while(i <= mid)temp[k++] = sum[i++];elsewhile(j <= r)temp[k++] = sum[j++];for(i = 0; i < k; ++i)sum[l++] = temp[i];return count;}
};

28 ms 12.2 MB

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/476431.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

AcWing之二维数组的查找

题目 在一个二维数组中&#xff0c;每一行都按照从左到右递增的顺序排序&#xff0c;每一列都按照从上到下递增的顺序排序。 请完成一个函数&#xff0c;输入这样的一个二维数组和一个整数&#xff0c;判断数组中是否含有该整数。样例 输入数组&#xff1a; [ [1,2,8,9]&…

sql server排序慢_SQL 查询调优之 where 条件排序字段以及 limit 使用索引的奥秘

(给数据分析与开发加星标&#xff0c;提升数据技能)作者&#xff1a;风过无痕-唐www.cnblogs.com/tangyanbo/p/6378741.html奇怪的慢sql我们先来看2条sql第一条&#xff1a;select * from acct_trans_log WHERE acct_id 1000000000009000757 order by create_time desc limit…

fedora10完全配置文档连接网址

code.google.com/p/fedora-zh/downloads/list 转载于:https://www.cnblogs.com/glc400/archive/2008/12/20/4473856.html

LeetCode 326. 3的幂

1. 题目 给定一个整数&#xff0c;写一个函数来判断它是否是 3 的幂次方。 示例 1: 输入: 27 输出: true示例 2: 输入: 0 输出: false示例 3: 输入: 9 输出: true示例 4: 输入: 45 输出: false进阶&#xff1a; 你能不使用循环或者递归来完成本题吗&#xff1f;来源&#xff…

ps抠头发插件_彻底告别抠图的烦恼!PS自动抠图超级插件Topaz ReMask大放送

我们经常需要对各种图片进行抠图&#xff0c;虽然抠图方法很多&#xff0c;但是我们却要花费很长的时间&#xff0c;这无疑来说效率非常不高。有没有一款PS插件可以快速对照片进行抠图&#xff1f;并且可以达到自己理想的效果&#xff1f;当然是有的&#xff0c;今天米朵就送给…

AcWing之找替换空格

题目 请实现一个函数&#xff0c;把字符串中的每个空格替换成"%20"。 你可以假定输入字符串的长度最大是1000。 注意输出字符串的长度可能大于1000。样例 输入&#xff1a;"We are happy."输出&#xff1a;"We%20are%20happy."方法一&#xff…

VC++中忽略所有默认库纯Win32 API编译及链接 - 计算机软件编程 - Wangye's Space

原始链接&#xff1a;VC中忽略所有默认库纯Win32 API编译及链接 - 计算机软件编程 - Wangyes Space 我们在用VC编写Windows程序的时候可能会发现一般可执行体&#xff08;.EXE&#xff09;的文件体积都比较大&#xff0c;于是非常羡慕那些使用Win32汇编编写程 序的人&#xff0…

LeetCode 345. 反转字符串中的元音字母

1. 题目 编写一个函数&#xff0c;以字符串作为输入&#xff0c;反转该字符串中的元音字母。 示例 1: 输入: "hello" 输出: "holle"示例 2: 输入: "leetcode" 输出: "leotcede"说明: 元音字母不包含字母"y"。来源&#xf…

python list存储对象_《python解释器源码剖析》第4章--python中的list对象

4.0 序python中的list对象&#xff0c;底层对应的则是PyListObject。如果你熟悉C&#xff0c;那么会很容易和C中的list联系起来。但实际上&#xff0c;这个C中的list大相径庭&#xff0c;反而和STL中的vector比较类似4.1 PyListObject对象我们知道python里面的list对象是支持对…

AcWing之从尾到头打印链表

题目 输入一个链表的头结点&#xff0c;按照 从尾到头 的顺序返回节点的值。 返回的结果用数组存储。样例 输入&#xff1a;[2, 3, 5] 返回&#xff1a;[5, 3, 2]方法一&#xff1a; /* struct ListNode {int val; //当前结点的值ListNode *next; //指向下一个结点的指针L…

javascript 打开新窗口

一、window.open()支持环境&#xff1a; JavaScript1.0/JScript1.0/Nav2/IE3/Opera3 二、基本语法&#xff1a;window.open(pageURL,name,parameters) 其中&#xff1a;pageURL 为子窗口路径 name 为子窗口句柄 parameters 为窗口参数(各参数用逗号分隔) 三、示例&#xff1a;…

python修改mac地址_python利用_winreg模块制作MAC地址修改工具

通过百度搜索知道&#xff0c;xp下修改MAC地址的方法主要有两个&#xff0c;一种是通过配置本地链接属性来实现&#xff0c;这种方法不适合用程序来完成&#xff0c;另一种是通过修改注册表来完成&#xff0c;本程序主要是利用了这种方法。具体方法&#xff1a;Windows 2000/XP…

我们为什么需要工作流

我们为什么需要工作流 这是我的"基于WF设计业务流程平台"的题外篇 以下是这系列的文章列表,写的很痛苦,但我会继续写下去 基于WF设计业务流程平台-架构 基于WF设计业务流程平台-权限体系 基于WF设计业务流程平台_特定群体与特定人 基于WF设计业务流程平台_参与者与任…

LeetCode 371. 两整数之和(位运算加法)

1. 题目 不使用运算符 和 - ​​​​​​​&#xff0c;计算两整数 ​​​​​​​a 、b ​​​​​​​之和。 示例 1: 输入: a 1, b 2 输出: 3示例 2: 输入: a -2, b 3 输出: 1来源&#xff1a;力扣&#xff08;LeetCode&#xff09; 链接&#xff1a;https://leetcod…

python函数方法里面用浅复制深复制_图解 Python 浅拷贝与深拷贝

Python 中的赋值语句不会创建对象的拷贝&#xff0c;仅仅只是将名称绑定至一个对象。对于不可变对象&#xff0c;通常没什么差别&#xff0c;但是处理可变对象或可变对象的集合时&#xff0c;你可能需要创建这些对象的 “真实拷贝”&#xff0c;也就是在修改创建的拷贝时不改变…

32位Windows系统未分页内存限制导致的VPS的容量问题

问题 32位Windows系统未分页内存限制导致的VPS的容量问题 解决方案 在32位的Windows系统上&#xff0c;制约VPS的数量的主要参数是“未分页内存” 打开Windows自己的任务管理器&#xff0c;选择性能标签&#xff0c;查看“核心内存”&#xff0c;查看“未分页” 在32位的windo…

AcWing之重建二叉树

题目 输入一棵二叉树前序遍历和中序遍历的结果&#xff0c;请重建该二叉树。 注意:二叉树中每个节点的值都互不相同&#xff1b;输入的前序遍历和中序遍历一定合法&#xff1b;样例 给定&#xff1a; 前序遍历是&#xff1a;[3, 9, 20, 15, 7] 中序遍历是&#xff1a;[9, 3, …

奇异值分解(Singular Value Decomposition,SVD)

文章目录1. 奇异值分解的定义与性质1.1 定义1.2 两种形式1.2.1 紧奇异值分解1.2.2 截断奇异值分解1.3 几何解释1.4 主要性质2. 奇异值分解与矩阵近似2.1 弗罗贝尼乌斯范数2.2 矩阵的最优近似2.3 矩阵的外积展开式3. 奇异值分解Python计算4. SVD应用一种矩阵因子分解方法矩阵的奇…

项目经理有必要学python吗_项目经理到底要不要懂技术

关于这个问题&#xff0c;我想开门见山地说一句&#xff0c;需要&#xff0c;而且非常需要。当然有同学就会说了&#xff0c;项目经理懂技术会被技术所束缚&#xff0c;无法跳出技术角度来看待项目整体。还有同学会说&#xff0c;现在是团队配合时代&#xff0c;各领域专精&…

贝叶斯算法

1. 贝叶斯由来 贝叶斯为了解决“逆概”问题提出的 2. 贝叶斯要解决的问题 正向概率 袋子里装着N个黑球和M个白球&#xff0c;伸手取摸球&#xff0c;摸到黑球和白球的概率有多大 逆向概率 袋子里前提不知道有黑白球的比例&#xff0c;而是闭着眼睛摸球统计后推测黑球和白球的…