洛谷P5524 区间加区间sin和(线段树)

upd: 它掉出 Ynoi 了,有时间了更几个真正的 Ynoi 吧。

Ynoi难得的很好写的题。主要考察两角和公式:

$\sin(\alpha+\beta)=\sin\alpha\cos\beta+\cos\alpha\sin\beta$

$\cos(\alpha+\beta)=\cos\alpha\cos\beta-\sin\alpha\sin\beta$

接下来就是线段树模板了:

#include<cstdio>
#include<cmath>
#define For(i,A,B) for(i=(A);i<=(B);++i)
typedef long long ll;
const int N=200050;
const int BUF=1<<21;
char rB[BUF],*rS,*rT;
inline char gc(){return rS==rT&&(rT=(rS=rB)+fread(rB,1,BUF,stdin),rS==rT)?EOF:*rS++;}
inline int rd(){
    char c=gc();
    while(c<48||c>57)c=gc();
    int x=c&15;
    for(c=gc();c>=48&&c<=57;c=gc())x=(x<<3)+(x<<1)+(c&15);
    return x;
}
int a[N],x,y,k;
double ssin[N<<2],scos[N<<2];
ll addv[N<<2];
inline void upd(int o,ll x){
    double sinx=sin(x),cosx=cos(x),t=ssin[o]*cosx+scos[o]*sinx;
    scos[o]=scos[o]*cosx-ssin[o]*sinx;
    ssin[o]=t;
    addv[o]+=x;
}
inline void pushup(int o){
    int lc=o<<1,rc=lc|1;
    ssin[o]=ssin[lc]+ssin[rc];scos[o]=scos[lc]+scos[rc];
}
inline void pushdown(int o){
    int lc=o<<1,rc=lc|1;
    upd(lc,addv[o]);upd(rc,addv[o]);
    addv[o]=0ll;
}
void build(int o,int L,int R){
    if(L==R){ssin[o]=sin(a[L]);scos[o]=cos(a[L]);}
    else{
        int lc=o<<1,rc=lc|1,M=L+R>>1;
        build(lc,L,M);build(rc,M+1,R);
        pushup(o);
    }
}
void add(int o,int L,int R){
    if(x<=L&&y>=R)upd(o,k);
    else{
        int lc=o<<1,rc=lc|1,M=L+R>>1;
        if(addv[o])pushdown(o);
        if(x<=M)add(lc,L,M);
        if(y>M)add(rc,M+1,R);
        pushup(o);
    }
}
double query(int o,int L,int R){
    if(x<=L&&y>=R)return ssin[o];
    int lc=o<<1,rc=lc|1,M=L+R>>1;
    double ans=0;
    if(addv[o])pushdown(o);
    if(x<=M)ans=query(lc,L,M);
    if(y>M)ans+=query(rc,M+1,R);
    return ans;
}
int main(){
    int n=rd(),q,i,opt;
    For(i,1,n)a[i]=rd();
    build(1,1,n);
    q=rd();
    while(q--){
        opt=rd();x=rd();y=rd();
        if(opt==1){
            k=rd();
            add(1,1,n);
        }else printf("%.1lf\n",query(1,1,n));
    }
    return 0;
}
View Code

 

posted @ 2020-03-14 08:40  wangyuchen  阅读(231)  评论(0编辑  收藏  举报