zoukankan      html  css  js  c++  java
  • poj 3468(线段树)

    http://poj.org/problem?id=3468

    题意:给n个数字,从A1 …………Am次命令,Q是查询,查询a到b的区间和,c是更新,从a到b每个值都增加x。
    思路:这是一个很明显的线段树的题目,就是线段树的用区间更新就可以,我也是第一次用。。

     1 #include <stdio.h>
     2 #include <string.h>
     3 #define maxn 100050
     4 
     5 long long arra[ maxn ];
     6 
     7 struct note{      //要用long long 类型的,不然会爆数据的。
     8 
     9     long long sum,c;
    10 
    11 }segtree[ maxn * 4 ];
    12 
    13 void build(int root , int instart , int iend)    //插入操作。
    14 {
    15     segtree[ root ].c = 0;
    16     if(instart == iend)
    17         segtree[ root ].sum = arra[ instart ];
    18     else
    19     {
    20         int mid = (instart + iend)/2;
    21         build( root * 2 , instart ,mid );
    22         build( root * 2 + 1 , mid + 1 , iend );
    23         segtree[ root ].sum = segtree[ root * 2 ].sum + segtree[ root *2 +1 ].sum;
    24     }
    25 }
    26 
    27 void pushdown(int root,int sta , int en )    //延迟标记。
    28 {
    29     if(segtree[ root ].c != 0)
    30     {
    31         segtree[ root * 2 ].c += segtree[ root ].c;
    32         segtree[ root * 2 + 1 ].c += segtree [ root ].c;
    33         int mid = (sta + en) / 2;
    34         segtree[ root * 2] .sum += segtree[ root ].c*( mid - sta + 1 );
    35         segtree[ root * 2 + 1 ].sum += segtree[ root ].c *( en - mid );
    36         segtree[ root ].c = 0;
    37     }
    38 }
    39 
    40 long long Find(int root , int ranges , int rangee , int goals ,int goale)     //查找。查找时也需要对延迟标记进行更新。
    41 {
    42     if( goals > rangee || goale < ranges)
    43         return 0;
    44     if( rangee <= goale && ranges >= goals)
    45         return segtree[ root ].sum;
    46     pushdown(root,ranges,rangee);
    47     int mid = (rangee+ranges) / 2;
    48     return Find(root * 2 , ranges , mid , goals ,goale)+ Find(root * 2 + 1, mid +1 , rangee , goals , goale );
    49 }
    50 
    51 
    52 
    53 
    54 void update(int root , int sta, int en,int x,int y,int val)          //更新。
    55 {
    56     if( x > en || y < sta)
    57         return ;
    58     if( x <= sta && y >= en)
    59     {
    60         segtree[ root ].sum += val*( en - sta + 1 ) ;
    61         segtree[ root ].c += val ;
    62         return ;
    63     }
    64         pushdown(root,sta,en);
    65         int mid = ( sta + en ) / 2;
    66             update ( root * 2 , sta , mid , x ,y ,val );
    67             update ( root * 2 + 1, mid + 1 , en , x , y , val );
    68         segtree [ root ].sum = segtree[ root * 2 ].sum + segtree[ root * 2 + 1 ].sum;
    69 }
    70 
    71 
    72 int main()
    73 {
    74     //freopen("in.txt","r",stdin);
    75     int m,n,a,b,c;
    76     char x;
    77     scanf("%d%d",&m,&n);
    78     for( int i = 1 ; i <= m ; i++ )
    79         scanf("%lld",&arra[i]);
    80         build(1,1,m);
    81     for( int i = 1 ; i <= n ; i++ )
    82     {
    83         scanf("%s",&x);
    84         if(x=='Q')
    85         {
    86             scanf("%d%d",&a,&b);
    87             printf("%lld
    ",Find(1,1,m,a,b));
    88         }
    89         else
    90         {
    91             scanf("%d%d%d",&a,&b,&c);
    92                 update(1,1,m,a,b,c);
    93         }
    94     }
    95     return 0;
    96 }
  • 相关阅读:
    R语言 逐步回归分析
    R语言 一元线性回归
    基于Qt的信号分析简单应用软件的设计
    【图论 5】图的应用——拓扑排序和关键路径
    【图论 3】图的应用——最小生成树
    B+树
    大概是最简明的B树博客了
    KMP算法
    【内存管理篇】基本分页存储管理方式
    双向链表为何时间复杂度为O(1)?
  • 原文地址:https://www.cnblogs.com/Tree-dream/p/5760786.html
Copyright © 2011-2022 走看看