2021-10-09 P1314 聪明的质检员

使用二分法解决质检问题
该博客讨论了一道可以通过二分法解决的质检题目,分析了二分法的三个关键点:情况单调性、答案浮动方式和答案求法。在实现过程中遇到的超时问题通过使用前缀和优化得到解决,同时提到了细节如二分查找中的边界处理和初始化值选择。文章还提及了其他可能的优化策略,如先判断后计算。

孱弱题解,请多支持

这题一眼望去,就可以确定:长的非常像二分答案(别问本孱弱怎么想的)。于是乎,我们就去思考二分答案的3个要点:

a.情况的单调性:

不难证明,当w越大时,我们的检验值y就越小。在明白了这一点时,我们才能确定这题可以用二分答案来处理。

b.二分答案的浮动方式(即当二分的情况符合条件时,我们应该怎么做):

由之前的推断可知:w越大,y越小。所以,当y>s时,我们就要考虑缩小所需的y,即增大w;当y<s时,我们就要考虑增大所需的y,即减小w。这样,我们的浮动方式就考虑好了。

c.答案的求法:

这往往是最难的一点。而本题则很良心:它已经给好了y的求法。按照题目所说的去做就行。

但是,当你愉快的打完代码,交上去后会“惊奇”的发现:一群大写的"T"立在了你的头上。很可惜,直接累计会超时。

那怎么优化呢?二分其本身自然是不好优化,那么我们从答案的求解上下手。

我们发现,由于l、所以包含的区间有可能重合,所以,我们经历了大量的重复计算。因此,我们可以用前缀和来提供快速运算。代码如下:

#include<bits/stdc++.h>
using namespace std;
#define N 200001
#define F(i,x,n) for(int i=x;i<=n;i++)
int n,m;
long long S;
int w[N],v[N];
long long stand;
long long s[N];
long long sum[N];
int l1[N],r1[N];
long long check(int mid){
	F(i,1,n){
		s[i]=0;
		sum[i]=0;
	}
	F(i,1,n){
		s[i]=s[i-1]+(w[i]>=mid);
		sum[i]=sum[i-1]+v[i]*(w[i]>=mid);
	}
	long long cnt=0;
	F(i,1,m){
		cnt+=(s[r1[i]]-s[l1[i]-1])*(sum[r1[i]]-sum[l1[i]-1]);
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值