SDOI2017相关分析

一道线段树水题

注意别被卡精度(无时无刻都要想着强制转换double)

居然写了(100min),我太弱了!!!

#include<bits/stdc++.h>
using namespace std;
inline int read(){
	int x=0,f=1;char c=getchar();
	while(!isdigit(c)){if(c=='-')f=-1;c=getchar();}
	while(isdigit(c)){x=(x<<1)+(x<<3)+(c^48);c=getchar();}
	return f==1?x:-x;
}
const int N=1e5+4;
#define lc (p<<1)
#define rc (p<<1|1)
int n,m,a[N],b[N];
double t[N<<2],tx[N<<2],dx[N<<2],dy[N<<2],lzmx[N<<2],lzmy[N<<2],lzcx[N<<2],lzcy[N<<2];
double ans,anx,ax,ay;
inline void pushup(int p){
	t[p]=t[lc]+t[rc];
	tx[p]=tx[lc]+tx[rc];
	dx[p]=dx[lc]+dx[rc];
	dy[p]=dy[lc]+dy[rc];
}
inline void pushmo(int p,int l,int r,double x,double y){
	t[p]+=dx[p]*y+dy[p]*x+x*y*(r-l+1);
	tx[p]+=x*2*dx[p]+x*x*(r-l+1);
	dx[p]+=x*(r-l+1);
	dy[p]+=y*(r-l+1);
	lzmx[p]+=x;
	lzmy[p]+=y;
}
inline double ii(double x){
	return x*(x+1)*(x*2+1)/6;
}
inline void pushco(int p,int l,int r,double x,double y){
	lzmx[p]=lzmy[p]=0;
	t[p]=ii(r)-ii(l-1)+(x+y)*(l+r)*(r-l+1)/2+x*y*(r-l+1);
	tx[p]=ii(r)-ii(l-1)+x*2*(l+r)*(r-l+1)/2+x*x*(r-l+1);
	dx[p]=x*(r-l+1)+(double)(l+r)*(r-l+1)/2;//double
	dy[p]=y*(r-l+1)+(double)(l+r)*(r-l+1)/2;
	lzcx[p]=x;lzcy[p]=y;
}
inline void pushdown(int p,int l,int mid,int r){
	if(lzcx[p]||lzcy[p]){
		pushco(lc,l,mid,lzcx[p],lzcy[p]);
		pushco(rc,mid+1,r,lzcx[p],lzcy[p]);
		lzcx[p]=lzcy[p]=0;
	}
	if(lzmx[p]||lzmy[p]){
		pushmo(lc,l,mid,lzmx[p],lzmy[p]);
		pushmo(rc,mid+1,r,lzmx[p],lzmy[p]);
		lzmx[p]=lzmy[p]=0;
	}
}
inline void build(int p,int l,int r){
	if(l==r){
		t[p]=(double)a[l]*b[l];
		tx[p]=(double)a[l]*a[l];
		dx[p]=a[l];
		dy[p]=b[l];
		return;
	}
	int mid=(l+r)>>1;
	build(lc,l,mid);
	build(rc,mid+1,r);
	pushup(p);
}
inline void modify(int p,int l,int r,int ql,int qr,double x,double y){
	if(ql<=l&&r<=qr){
		pushmo(p,l,r,x,y);
		return;
	}
	int mid=l+r>>1;
	pushdown(p,l,mid,r);
	if(ql<=mid)modify(lc,l,mid,ql,qr,x,y);
	if(mid<qr)modify(rc,mid+1,r,ql,qr,x,y);
	pushup(p);
}
inline void cover(int p,int l,int r,int ql,int qr,double x,double y){
	if(ql<=l&&r<=qr){
		pushco(p,l,r,x,y);
		return;
	}
	int mid=l+r>>1;
	pushdown(p,l,mid,r);
	if(ql<=mid)cover(lc,l,mid,ql,qr,x,y);
	if(mid<qr)cover(rc,mid+1,r,ql,qr,x,y);
	pushup(p);
}
inline void query(int p,int l,int r,int ql,int qr){
	if(ql<=l&&r<=qr){
		ans+=t[p];
		anx+=tx[p];
		ax+=dx[p];
		ay+=dy[p]; 
		return;
	}
	int mid=l+r>>1;
	pushdown(p,l,mid,r);
	if(ql<=mid)query(lc,l,mid,ql,qr);
	if(mid<qr)query(rc,mid+1,r,ql,qr);
}
int main(){
	n=read();m=read();
	for(int i=1;i<=n;i++)a[i]=read();
	for(int i=1;i<=n;i++)b[i]=read();
	build(1,1,n);
	while(m--){
		static int op,l,r,x,y;
		op=read();l=read();r=read();
		if(op==1){
			ans=anx=ax=ay=0;
			query(1,1,n,l,r);
			l=r-l+1;
			printf("%.8lf
",(ans-ax*ay/l)/(anx-ax*ax/l));
			continue;
		}
		x=read();y=read();
		if(op==2)modify(1,1,n,l,r,x,y);
		else cover(1,1,n,l,r,x,y);
	}
	return (0-0);
}
原文地址:https://www.cnblogs.com/aurora2004/p/12518386.html