样例醛过求调
查看原帖
样例醛过求调
1420626
UrakSu楼主2025/7/21 19:24
#include<bits/stdc++.h>
#define pl (p<<1)
#define pr (p<<1|1)
using namespace std;
const int N = 2e5+10;

struct str{
	long long tag;
	double co,si;
}tr[N<<2];
int n,m;
void up(int p){
	tr[p].si = tr[pl].si + tr[pr].si;
	tr[p].co = tr[pl].co + tr[pr].co;
}
void build(int p,int l,int r){
	if(l == r){
		register int x;cin >> x;
		tr[p].si = sin(x),tr[p].co = cos(x);
		return;
	}
	int mid = (l+r)>>1;
	build(pl,l,mid);
	build(pr,mid+1,r);
	up(p);
}
void add_tag(int p,int v){
	double cos_ = tr[p].co * cos(v) - tr[p].si * sin(v),
		   sin_ = tr[p].si * cos(v) + tr[p].co * sin(v);
	tr[p].tag += v,tr[p].co = cos_,tr[p].si = sin_;
}
void down(int p){
	add_tag(pl,tr[p].tag),add_tag(pr,tr[p].tag);
	tr[p].tag = 0;
}
void add(int p,int l,int r,int L,int R,int v){
	if(L <= l && r <= R){
		add_tag(p,v);
		return;
	}
	int mid = (l+r)>>1;
	down(p);
	if(mid >= L) add(pl,l,mid,L,R,v);
	if(mid+1<=R) add(pr,mid+1,r,L,R,v);
	up(p);
}
double sum(int p,int l,int r,int L,int R){
	if(L <= l && r <= R) return tr[p].si;
	int mid = (l+r)>>1;
	down(p);
	double ret = 0;
	if(mid >= L) ret += sum(pl,l,mid,L,R);
	if(mid+1<=R) ret += sum(pr,mid+1,r,L,R);
	return ret;
}
int main(){
	ios::sync_with_stdio();
	cin >> n;
	build(1,1,n);
	cin >> m;
	while(m--){
		register int k,l,r,v;
		cin >> k;
		switch(k){
			case 1:
				cin >> l >> r >> v;
				add(1,1,n,l,r,v);
				break;
			case 2:
				cin >> l >> r;
				printf("%.1f\n",sum(1,1,n,l,r));
				break;
		}
	}
	return 0;
}
2025/7/21 19:24
加载中...