「CSP-J/S2022模拟赛7.8 D」平凡的我

「CSP-J/S2022模拟赛7.8 D」平凡的我

给定一个长度为 N 的数组 AQ 次操作:

  1. 单点修改 A_p = v
  2. 查询 a[l] + a[l+1] + \cdots a[r] 的历史最小值。

N,Q\leq 1.2\times 10^5

Tutorial(K-D Tree / 四分树)

考虑建立以 l,r 为两轴的平面以维护答案。

查询即为查询该平面上的一点的权值。

修改操作即修改满足 l\leq p \leq r 的所有 [l,r] 点的权值,显然这是一个矩形。

那么我们就变成了矩阵修改,单点查询问题。

每个点维护当前值以及最小值,用 K-D Tree / 四分树 维护即可。

时间复杂度:O(N\sqrt N)

Tutorial(莫队 + 线段树)

把所有操作离线。

考虑每个操作添加“时间戳”关键字。

那么我们用莫队维护出当前区间 [l,r],在线段树上以时间戳为下标,维护前缀和的最小值。

这个可以化为区间修改,区间查询,不难做到。

可以调调块长,把 \log 丢到根号里,可以做到。

时间复杂度 O(N\sqrt{N\log N})

但由于其巨大的常数,跑起来比 K-D Tree 慢很多。

但四分树由于其丑陋的结构,甚至无法足以通过本题。

Solution(莫队 + 线段树)

#pragma GCC optimize(2)
#include<bits/stdc++.h>
#define Tp template<typename Ty>
#define Ts template<typename Ty,typename... Ar>
#define W while
#define I inline
#define RI register int
#define LL long long
#define Cn const
#define CI Cn int&
using namespace std;
namespace Debug{
	Tp I void _debug(Cn char* f,Ty t){cerr<<f<<'='<<t<<endl;}
	Ts I void _debug(Cn char* f,Ty x,Ar... y){W(*f!=',') cerr<<*f++;cerr<<'='<<x<<",";_debug(f+1,y...);}
	Tp ostream& operator<<(ostream& os,Cn vector<Ty>& V){os<<"[";for(Cn auto& vv:V) os<<vv<<",";os<<"]";return os;}
	#define gdb(...) _debug(#__VA_ARGS__,__VA_ARGS__)
}using namespace Debug;
namespace FastIO{
	#define FS 100000
	#define tc() (FA==FB&&(FB=(FA=FI)+fread(FI,1,FS,stdin),FA==FB)?EOF:*FA++)
	#define pc(c) (FC==FE&&(clear(),0),*FC++=c)
	int OT;char oc,FI[FS],FO[FS],OS[FS],*FA=FI,*FB=FI,*FC=FO,*FE=FO+FS;
	I void clear() {fwrite(FO,1,FC-FO,stdout),FC=FO;}
	Tp I void read(Ty& x) {x=0;W(!isdigit(oc=tc()));W(x=(x<<3)+(x<<1)+(oc&15),isdigit(oc=tc()));}
	Ts I void read(Ty& x,Ar&... y) {read(x),read(y...);}
	Tp I void writeln(Ty x) {W(OS[++OT]=x%10+48,x/=10);W(OT) pc(OS[OT--]);pc('\n');}
}using namespace FastIO;
Cn int N=1.2e5+10,M=N;
int n,Qt,a[N],rt,bl[N],cnt;LL s[N],Ans[N];
struct Que{int l,r,id;}q[N];
class SegmentTree{
	private:
		LL T[N<<2],tg[N<<2];
		#define mid (l+r>>1)
		#define PT CI x=1,CI l=1,CI r=Qt
		#define LT x<<1,l,mid
		#define RT x<<1|1,mid+1,r
		#define PU(x) (T[x]=min(T[x<<1],T[x<<1|1]))
		#define AP(x,v) (T[x]+=v,tg[x]+=v)
		I void PD(CI x){tg[x]&&(AP(x<<1,tg[x]),AP(x<<1|1,tg[x]),tg[x]=0);}
	public:
		I void U(CI L,CI R,LL v,PT){
			if(L<=l&&r<=R) return AP(x,v),void();
			PD(x),L<=mid&&(U(L,R,v,LT),0),R>mid&&(U(L,R,v,RT),0),PU(x);
		}
		I LL Q(CI L,CI R,PT){
			if(L<=l&&r<=R) return T[x];
			LL X=0;return PD(x),L<=mid&&(X=min(X,Q(L,R,LT))),R>mid&&(X=min(X,Q(L,R,RT))),X;
		}
}T;
#define pa pair<int,int>
#define mp make_pair
#define fi first
#define se second
vector<pa> v[N];
#define pb push_back
I void add(CI x){
	for(auto i:v[x]) /*gdb(i.se,i.fi),*/T.U(i.se,n,i.fi);
}
I void del(CI x){
	for(auto i:v[x]) /*gdb(i.se,-i.fi),*/T.U(i.se,n,-i.fi);
}
int main(){
	RI i,o,l,r,S;for(read(n,Qt),S=sqrt(n*6),gdb(S),i=1;i<=n;i++) read(a[i]),s[i]=s[i-1]+a[i];for(i=1;i<=Qt;i++)
		read(o,l,r),o&1?v[l].pb(mp(r-a[l],i)),a[l]=r:(q[++cnt]={l,r,i},0);
	for(i=1;i<=n;i++) bl[i]=(i-1)/S+1;memset(Ans,-1,sizeof(Ans));
	for(sort(q+1,q+cnt+1,[&](Cn Que& x,Cn Que& y){return bl[x.l]^bl[y.l]?x.l<y.l:bl[x.l]&1?x.r<y.r:x.r>y.r;}),l=1,r=0,i=1;i<=cnt;i++){
		W(l>q[i].l) add(--l);W(r<q[i].r) add(++r);W(l<q[i].l) del(l++);W(r>q[i].r) del(r--);
		// cerr<<"Q "<<q[i].id<<" "<<T.Q(1,q[i].id)<<endl;
		Ans[q[i].id]=min(T.Q(1,q[i].id),0LL)+s[q[i].r]-s[q[i].l-1];
	}for(i=1;i<=Qt;i++) ~Ans[i]&&(writeln(Ans[i]),0);
	return clear(),cerr<<clock()<<"ms\n",0;
}

Solution(四分树)

#include<bits/stdc++.h>
#define Tp template<typename Ty>
#define Ts template<typename Ty,typename... Ar>
#define W while
#define I inline
#define RI register int
#define LL long long
#define Cn const
#define CI Cn int&
using namespace std;
namespace Debug{
	Tp I void _debug(Cn char* f,Ty t){cerr<<f<<'='<<t<<endl;}
	Ts I void _debug(Cn char* f,Ty x,Ar... y){W(*f!=',') cerr<<*f++;cerr<<'='<<x<<",";_debug(f+1,y...);}
	Tp ostream& operator<<(ostream& os,Cn vector<Ty>& V){os<<"[";for(Cn auto& vv:V) os<<vv<<",";os<<"]";return os;}
	#define gdb(...) _debug(#__VA_ARGS__,__VA_ARGS__)
}using namespace Debug;
namespace FastIO{
	#define FS 100000
	#define tc() (FA==FB&&(FB=(FA=FI)+fread(FI,1,FS,stdin),FA==FB)?EOF:*FA++)
	#define pc(c) (FC==FE&&(clear(),0),*FC++=c)
	int OT;char oc,FI[FS],FO[FS],OS[FS],*FA=FI,*FB=FI,*FC=FO,*FE=FO+FS;
	I void clear() {fwrite(FO,1,FC-FO,stdout),FC=FO;}
	Tp I void read(Ty& x) {x=0;W(!isdigit(oc=tc()));W(x=(x<<3)+(x<<1)+(oc&15),isdigit(oc=tc()));}
	Ts I void read(Ty& x,Ar&... y) {read(x),read(y...);}
	Tp I void writeln(Ty x) {W(OS[++OT]=x%10+48,x/=10);W(OT) pc(OS[OT--]);pc('\n');}
}using namespace FastIO;
Cn int N=1.2e5+10,M=N;
int n,Q,a[N],rt;LL s[N];
struct Que{int o,l,r,id;}q[N];
class SegmentTree{
	private:
		int cnt;
		struct node{int son[4];LL S,T,A;}T[M*40];
		#define midX (a+c>>1)
		#define midY (b+d>>1)
		#define S0 T[x].son[0],a,b,midX,midY
		#define S1 T[x].son[1],midX+1,b,c,midY
		#define S2 T[x].son[2],a,midY+1,midX,d
		#define S3 T[x].son[3],midX+1,midY+1,c,d
		#define PU(x) (T[x].S=T[T[x].son[0]].S+T[T[x].son[1]].S+T[T[x].son[2]].S+T[T[x].son[3]].S)
		I void PD(CI x){
			T[x].T&&(
			T[x].son[0]&&(T[x].T>0&&T[T[x].son[0]].T<0&&(PD(T[x].son[0]),0),T[T[x].son[0]].S+=T[x].T,T[T[x].son[0]].T+=T[x].T,T[T[x].son[0]].A=min(T[T[x].son[0]].A,T[T[x].son[0]].S),0),
			T[x].son[1]&&(T[x].T>0&&T[T[x].son[1]].T<0&&(PD(T[x].son[1]),0),T[T[x].son[1]].S+=T[x].T,T[T[x].son[1]].T+=T[x].T,T[T[x].son[1]].A=min(T[T[x].son[1]].A,T[T[x].son[1]].S),0),
			T[x].son[2]&&(T[x].T>0&&T[T[x].son[2]].T<0&&(PD(T[x].son[2]),0),T[T[x].son[2]].S+=T[x].T,T[T[x].son[2]].T+=T[x].T,T[T[x].son[2]].A=min(T[T[x].son[2]].A,T[T[x].son[2]].S),0),
			T[x].son[3]&&(T[x].T>0&&T[T[x].son[3]].T<0&&(PD(T[x].son[3]),0),T[T[x].son[3]].S+=T[x].T,T[T[x].son[3]].T+=T[x].T,T[T[x].son[3]].A=min(T[T[x].son[3]].A,T[T[x].son[3]].S),0),
			T[x].T=0);
		}
	public:
		I void B(int &x,CI a,CI b,CI c,CI d,CI Qa,CI Qb,CI Qc,CI Qd){
			!x&&(x=++cnt);if(Qa<=a&&Qb<=b&&c<=Qc&&d<=Qd) return ;
			Qa<=midX&&Qb<=midY&&(B(S0,Qa,Qb,min(Qc,midX),min(Qd,midY)),0),
			Qc>midX&&Qb<=midY&&(B(S1,max(Qa,midX+1),Qb,Qc,min(Qd,midY)),0),
			Qa<=midX&&Qd>midY&&(B(S2,Qa,max(Qb,midY+1),min(Qc,midX),Qd),0),
			Qc>midX&&Qd>midY&&(B(S3,max(Qa,midX+1),max(Qb,midY+1),Qc,Qd),0);
		}
		I void U(int& x,CI a,CI b,CI c,CI d,CI Qa,CI Qb,CI Qc,CI Qd,LL v){
			if(!x) return ;if(Qa<=a&&Qb<=b&&c<=Qc&&d<=Qd) return T[x].T<0&&v>0&&(PD(x),0),T[x].S+=v,T[x].T+=v,T[x].A=min(T[x].A,T[x].S),void();
			PD(x),Qa<=midX&&Qb<=midY&&(U(S0,Qa,Qb,min(Qc,midX),min(Qd,midY),v),0),
			Qc>midX&&Qb<=midY&&(U(S1,max(Qa,midX+1),Qb,Qc,min(Qd,midY),v),0),
			Qa<=midX&&Qd>midY&&(U(S2,Qa,max(Qb,midY+1),min(Qc,midX),Qd,v),0),
			Qc>midX&&Qd>midY&&(U(S3,max(Qa,midX+1),max(Qb,midY+1),Qc,Qd,v),0),PU(x);
		}
		I LL Q(int &x,CI a,CI b,CI c,CI d,CI Qa,CI Qb,CI Qc,CI Qd){
			if(Qa<=a&&Qb<=b&&c<=Qc&&d<=Qd) return T[x].A;
			LL S=0;return PD(x),Qa<=midX&&Qb<=midY&&(S+=Q(S0,Qa,Qb,min(Qc,midX),min(Qd,midY))),
			Qc>midX&&Qb<=midY&&(S+=Q(S1,max(Qa,midX+1),Qb,Qc,min(Qd,midY))),
			Qa<=midX&&Qd>midY&&(S+=Q(S2,Qa,max(Qb,midY+1),min(Qc,midX),Qd)),
			Qc>midX&&Qd>midY&&(S+=Q(S3,max(Qa,midX+1),max(Qb,midY+1),Qc,Qd)),S;
		}
}S;
int main(){
	RI i,o,l,r;for(read(n,Q),i=1;i<=n;i++) read(a[i]),s[i]=s[i-1]+a[i];for(i=1;i<=Q;i++) read(q[i].o,q[i].l,q[i].r);
	for(i=1;i<=Q;i++) !(q[i].o&1)&&(S.B(rt,1,1,n,n,q[i].l,q[i].r,q[i].l,q[i].r),0);
	for(i=1;i<=Q;i++) q[i].o&1?(S.U(rt,1,1,n,n,1,q[i].l,q[i].l,n,q[i].r-a[q[i].l]),a[q[i].l]=q[i].r,0):(writeln(s[q[i].r]-s[q[i].l-1]+S.Q(rt,1,1,n,n,q[i].l,q[i].r,q[i].l,q[i].r)),0);
	return clear(),0;
},0);
	return clear(),cerr<<clock()<<"ms\n",0;
}

原文地址:https://cloud.tencent.com/developer/article/2111482

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


学习编程是顺着互联网的发展潮流,是一件好事。新手如何学习编程?其实不难,不过在学习编程之前你得先了解你的目的是什么?这个很重要,因为目的决定你的发展方向、决定你的发展速度。
IT行业是什么工作做什么?IT行业的工作有:产品策划类、页面设计类、前端与移动、开发与测试、营销推广类、数据运营类、运营维护类、游戏相关类等,根据不同的分类下面有细分了不同的岗位。
女生学Java好就业吗?女生适合学Java编程吗?目前有不少女生学习Java开发,但要结合自身的情况,先了解自己适不适合去学习Java,不要盲目的选择不适合自己的Java培训班进行学习。只要肯下功夫钻研,多看、多想、多练
Can’t connect to local MySQL server through socket \'/var/lib/mysql/mysql.sock问题 1.进入mysql路径
oracle基本命令 一、登录操作 1.管理员登录 # 管理员登录 sqlplus / as sysdba 2.普通用户登录
一、背景 因为项目中需要通北京网络,所以需要连vpn,但是服务器有时候会断掉,所以写个shell脚本每五分钟去判断是否连接,于是就有下面的shell脚本。
BETWEEN 操作符选取介于两个值之间的数据范围内的值。这些值可以是数值、文本或者日期。
假如你已经使用过苹果开发者中心上架app,你肯定知道在苹果开发者中心的web界面,无法直接提交ipa文件,而是需要使用第三方工具,将ipa文件上传到构建版本,开...
下面的 SQL 语句指定了两个别名,一个是 name 列的别名,一个是 country 列的别名。**提示:**如果列名称包含空格,要求使用双引号或方括号:
在使用H5混合开发的app打包后,需要将ipa文件上传到appstore进行发布,就需要去苹果开发者中心进行发布。​
+----+--------------+---------------------------+-------+---------+
数组的声明并不是声明一个个单独的变量,比如 number0、number1、...、number99,而是声明一个数组变量,比如 numbers,然后使用 nu...
第一步:到appuploader官网下载辅助工具和iCloud驱动,使用前面创建的AppID登录。
如需删除表中的列,请使用下面的语法(请注意,某些数据库系统不允许这种在数据库表中删除列的方式):
前不久在制作win11pe,制作了一版,1.26GB,太大了,不满意,想再裁剪下,发现这次dism mount正常,commit或discard巨慢,以前都很快...
赛门铁克各个版本概览:https://knowledge.broadcom.com/external/article?legacyId=tech163829
实测Python 3.6.6用pip 21.3.1,再高就报错了,Python 3.10.7用pip 22.3.1是可以的
Broadcom Corporation (博通公司,股票代号AVGO)是全球领先的有线和无线通信半导体公司。其产品实现向家庭、 办公室和移动环境以及在这些环境...
发现个问题,server2016上安装了c4d这些版本,低版本的正常显示窗格,但红色圈出的高版本c4d打开后不显示窗格,
TAT:https://cloud.tencent.com/document/product/1340