zoukankan      html  css  js  c++  java
  • P6327 区间加区间sin和

    Problem

    维护一个序列(a),每次操作有两种类型:

    • 1 l r v(a_l sim a_r)的所有数加(v)
    • 2 l r(sum_{i = l} ^ r sin (a_i))
      输入数据均小于(2 imes 10^5)

    Solution

    上午刚做完一个Ynoi,以为是最简单的Ynoi题了,结果这题更是重量级。
    不难发现通过两个诱导公式可以做:

    [sin(alpha + eta) = sin(alpha) cos(eta) + sin(eta)cos(alpha)\ cos(alpha + eta) = cos(alpha) cos(eta) - sin(alpha) sin(eta) ]

    然后用线段树,节点维护sin,cos和即可。

    # include <bits/stdc++.h>
    using namespace std;
    const int N = 2e5 + 5;
    int n;
    double a[N];
    int m;
    struct node
    {
        double Sin,Cos,lazy;
    }T[N << 2];
    void pushup(int root)
    {
    
        T[root].Sin = T[root << 1].Sin + T[root << 1 | 1].Sin;
        T[root].Cos = T[root << 1].Cos + T[root << 1 | 1].Cos;
        return;
    }
    void build(int root,int l,int r)
    {
        if(l == r)
        {
            T[root].Sin = sin(a[l]),T[root].Cos = cos(a[l]);
            T[root].lazy = 0;
            return;
        }
        int mid = (l + r) >> 1;
        build(root << 1,l,mid),build(root << 1 | 1, mid + 1, r);
        pushup(root);
        return;
    }
    void pushdown(int root)
    {
        if(T[root].lazy == 0) return;
        double tag = T[root].lazy;
        double sine = sin(tag),cosine = cos(tag);
        double sn = T[root << 1].Sin,cs = T[root << 1].Cos;
        T[root << 1].Sin = sn * cosine + sine * cs;
        T[root << 1].Cos = cosine * cs - sine * sn;
        sn = T[root << 1 | 1].Sin,cs = T[root << 1 | 1].Cos;
        T[root << 1 | 1].Sin = sn * cosine + sine * cs;
        T[root << 1 | 1].Cos = cosine * cs - sine * sn;
        T[root << 1].lazy += tag,T[root << 1 | 1].lazy += tag;
        T[root].lazy = 0;
        return;
    }
    void update(int root,int l,int r,int s,int t,double d)
    {
        if(l <= s && t <= r)
        {
            double sine = sin(d),cosine = cos(d);
            double sn = T[root].Sin,cs = T[root].Cos;
            T[root].Sin = sn * cosine + sine * cs;
            T[root].Cos = cosine * cs - sine * sn;
            T[root].lazy += d;
            return;
        }
        pushdown(root);
        int mid = (s + t) >> 1;
        if(l <= mid) update(root << 1,l,r,s,mid,d);
        if(r > mid) update(root << 1 | 1,l,r,mid + 1,t,d);
        pushup(root);
        return;
    }
    double query(int root,int l,int r,int s,int t)
    {
        if(l <= s && t <= r) return T[root].Sin;
        pushdown(root);
        int mid = (s + t) >> 1;
        double ans = 0;
        if(l <= mid) ans = ans + query(root << 1,l,r,s,mid);
        if(r > mid) ans = ans + query(root << 1 | 1,l,r,mid + 1,t);
        return ans;
    }
    int main(void)
    {
        scanf("%d",&n);
        for(int i = 1; i <= n; i++) scanf("%lf",&a[i]);
        build(1,1,n);
        scanf("%d",&m);
        while(m--)
        {
            int opt,l,r;
            scanf("%d%d%d",&opt,&l,&r);
            if(opt == 1)
            {
                double v; scanf("%lf",&v);
                update(1,l,r,1,n,v);
            }
            else 
            {
                printf("%.1lf
    ",query(1,l,r,1,n));
            }
        }
        return 0;
    }
    
  • 相关阅读:
    从.NET到Mono-记Kooboo CMS对Mono的兼容历程:二、大小写敏感问题,到处都是地雷
    发布NBear.Mapping 开源通用映射组件 V1.0.1.8 beta
    发布支持代理,以及解决登录可能出现异常的DotMSN(强烈建议改用MSNPSharp来开发)
    LumaQQ.NET 2008 更新
    从.NET到Mono-记Kooboo CMS对Mono的兼容历程:三、平台的兼容性
    网站架构资料收集整理 Virus
    项目团队技术个人(提拔篇) Virus
    [翻译].NET框架中的缓存 Virus
    培养我们的目标感 Virus
    使用Django来处理对于静态文件的请求 Virus
  • 原文地址:https://www.cnblogs.com/luyiming123blog/p/15187426.html
Copyright © 2011-2022 走看看