求助/kel
  • 板块P1471 方差
  • 楼主Prean
  • 当前回复10
  • 已保存回复10
  • 发布时间2020/11/14 15:48
  • 上次更新2023/11/5 08:04:57
查看原帖
求助/kel
160839
Prean楼主2020/11/14 15:48

RT,维护 区间平方和 和 区间和,全 WA 求助/kel

#include<cstdio>
typedef double db;
const int M=1e5+5;
int n,m;
db val,a[M];
struct Node{
	db sum,squ,tag;
	inline Node operator+(const Node&it)const{
		return (Node){sum+it.sum,squ+it.squ,0};
	}
}tmp,t[M<<2];
inline void update(const int&u){
	t[u]=t[u<<1]+t[u<<1|1];
}
inline void pushdown(const int&u,const int&L,const int&R){
	if(!t[u].tag)return;
	int mid=L+R>>1;
	const int&k=t[u].tag;
	t[u<<1].squ+=k*k*(mid-L+1)+2*k*t[u<<1].sum;
	t[u<<1|1].squ+=k*k*(R-mid)+2*k*t[u<<1|1].sum;
	t[u<<1].tag+=t[u].tag;t[u<<1].sum+=(mid-L+1)*t[u].tag;
	t[u<<1|1].tag+=t[u].tag;t[u<<1|1].sum+=(R-mid)*t[u].tag;
	t[u].tag=0;
}
void build(int u,int L,int R){
	if(L==R)t[u].sum=a[L],t[u].squ=1ll*a[L]*a[L];
	else{
		int mid=L+R>>1;
		build(u<<1,L,mid);build(u<<1|1,mid+1,R);
		update(u);
	}
}
void Modify(int u,int l,int r,db val,int L=1,int R=n){
	if(L>r||l>R)return;
	if(l<=L&&R<=r){
		t[u].tag+=val;
		t[u].squ+=val*val*(R-L+1)+2*val*t[u].sum;
		t[u].sum+=val*(R-L+1);
		return;
	}
	int mid=L+R>>1;
	pushdown(u,L,R);
	Modify(u<<1,l,r,val,L,mid);Modify(u<<1|1,l,r,val,mid+1,R);
	update(u);
}
Node Query(int u,int l,int r,int L=1,int R=n){
	if(L>r||l>R)return (Node){0,0,0};
	if(l<=L&&R<=r)return t[u];
	int mid=L+R>>1;
	pushdown(u,L,R);
	return Query(u<<1,l,r,L,mid)+Query(u<<1|1,l,r,mid+1,R);
}
signed main(){
	register int i,f,L,R;
	scanf("%d%d",&n,&m);
	for(i=1;i<=n;++i)scanf("%lf",a+i);
	build(1,1,n);
	for(i=1;i<=m;++i){
		scanf("%d%d%d",&f,&L,&R);
		if(f==1){
			scanf("%lf",&val);
			Modify(1,L,R,val);
		}
		else if(f==2){
			printf("%.4lf\n",Query(1,L,R).sum/(R-L+1));
		}
		else{
			tmp=Query(1,L,R);
			val=tmp.sum/(R-L+1);
			printf("%.4lf\n",(tmp.squ-2*val*tmp.sum)/(R-L+1)+val*val);
		}
	}
}
2020/11/14 15:48
加载中...