• HDOJ 4267 A Simple Problem with Integers (线段树)


    题目:

    Problem Description
    Let A1, A2, ... , AN be N elements. You need to deal with two kinds of operations. One type of operation is to add a given number to a few numbers in a given interval. The other is to query the value of some element.
     
    Input
    There are a lot of test cases. The first line contains an integer N. (1 <= N <= 50000) The second line contains N numbers which are the initial values of A1, A2, ... , AN. (-10,000,000 <= the initial value of Ai <= 10,000,000) The third line contains an integer Q. (1 <= Q <= 50000) Each of the following Q lines represents an operation. "1 a b k c" means adding c to each of Ai which satisfies a <= i <= b and (i - a) % k == 0. (1 <= a <= b <= N, 1 <= k <= 10, -1,000 <= c <= 1,000) "2 a" means querying the value of Aa. (1 <= a <= N)
     
    Output
    For each test case, output several lines to answer all query operations.
     
    Sample Input
    4
    1 1 1 1
    14
    2 1
    2 2
    2 3
    2 4
    1 2 3 1 2
    2 1
    2 2
    2 3
    2 4
    1 1 4 2 1
    2 1
    2 2
    2 3
    2 4
     
    Sample Output
    1
    1
    1
    1
    1
    3
    3
    1
    2
    3
    4
    1
    思路:
    区间修改 单点查询
    第一个操作是 对在a-b区间内的位置i 如果满足(i-a)%k==0 就把这个位置上的值加上c
    式子可以等同于i%k==a%k 所以问题就转化为了右边的部分
    从数据范围中可以看到k的范围很小 对k进行枚举 
    k=1时 可以取的余数为0,1 
    k=2时 可以取的余数为0,1 ,2
    以此类推 所有可以取的结果共55种 根据取余的情况 对这一个区间内该更新哪些线段树进行纪录 然后对这一棵线段树这个区间内的所有值进行更新
    代码:
    #include <iostream>
    #include <cstdio>
    #include <cstdlib>
    #include <cmath>
    #include <string>
    #include <cstring>
    #include <algorithm>
    
    using namespace std;
    typedef long long ll;
    typedef unsigned long long ull;
    const int inf=0x3f3f3f3f;
    const int maxn=5e4+10;
    int n,m,y,a,b,k,c,op,ans;
    int x[maxn];
    
    struct node{
        int l,r,w;
        int add[55];
    }tree[maxn<<2];
    
    void build(int l,int r,int rt){
        tree[rt].l=l;
        tree[rt].r=r;
        memset(tree[rt].add,0,sizeof(tree[rt].add));
        if(l==r){
            tree[rt].w=x[l];
            return;
        }
        int mid=(l+r)/2;
        build(l,mid,rt*2);
        build(mid+1,r,rt*2+1);
        tree[rt].w=tree[rt*2].w+tree[rt*2+1].w;
    }
    
    void pushdown(int rt){
        tree[rt*2].w+=tree[rt].w;
        tree[rt*2+1].w+=tree[rt].w;
        tree[rt].w=0;
        for(int i=0;i<55;i++){
            tree[rt*2].add[i]+=tree[rt].add[i];
            tree[rt*2+1].add[i]+=tree[rt].add[i];
            tree[rt].add[i]=0;
        }
    }
    
    void update(int tmp,int rt){
        if(tree[rt].l>=a && tree[rt].r<=b){
            int index=k*(k-1)/2+tmp;
            tree[rt].add[index]+=c;
            tree[rt].w+=c;
            return;
        }
        if(tree[rt].w) pushdown(rt);
        int mid=(tree[rt].l+tree[rt].r)/2;
        if(a<=mid) update(tmp,rt*2);
        if(b>mid) update(tmp,rt*2+1);
    //    tree[rt].w=tree[rt*2].w+tree[rt*2+1].w;
    }
    
    void query(int rt){
        if(tree[rt].l==y && tree[rt].r==y){
            for(int i=1;i<=10;i++){
                int index=i*(i-1)/2+y%i;
                ans+=tree[rt].add[index];
            }
            return;
        }
        if(tree[rt].w) pushdown(rt);
        int mid=(tree[rt].l+tree[rt].r)/2;
        if(y<=mid) query(rt*2);
        else query(rt*2+1);
    }
    
    int main(){
        while(~scanf("%d",&n)){
            for(int i=1;i<=n;i++){
                scanf("%d",&x[i]);
            }
            build(1,n,1);
            scanf("%d",&m);
            for(int i=1;i<=m;i++){
                scanf("%d",&op);
                if(op==1){
                    scanf("%d%d%d%d",&a,&b,&k,&c);
                    update(a%k,1);
                }
                if(op==2){
                    ans=0;
                    scanf("%d",&y);
                    query(1);
                    printf("%d
    ",x[y]+ans);
                }
            }
        }
        return 0;
    }
     
  • 相关阅读:
    Azure 虚拟机诊断设置问题排查
    虚拟机压力测试延迟高的可能原因及 ILPIP 配置 / 查询脚本
    理解 Azure 平台中虚拟机的计算能力
    如何复制或导出托管磁盘
    理解托管磁盘的原理与优势
    Azure 托管镜像和非托管镜像对比
    如何将同一云服务下的虚拟机从经典部署模型迁移到 Azure Resource Manager
    如何将同一 VNET 下的虚拟机从经典部署模型迁移到 Azure Resource Manager
    如何将使用托管磁盘虚拟机的 OS 盘挂载到其他虚拟机上
    基于 Azure 托管磁盘配置高可用共享文件系统
  • 原文地址:https://www.cnblogs.com/whdsunny/p/10463770.html
Copyright © 2020-2023  润新知