poj 3468 A Simple Problem with Integers

来源:互联网 发布:电视视频端口坏掉 编辑:程序博客网 时间:2024/06/06 07:01

题目大意:给你一串数字,和一堆询问,分别是问一段区间的和,和给某段数字每个数字增加一定的值。

解题思路:用暴力做肯定会超时,所以用线段树或者树状数组都可以做。这里为了练习线段树就用线段树做了。

线段树的思路就是将当前区间二分成一颗二叉树,通过区间的合并和分解来实现对区间值的修改。

做出来的第一个线段树,纪念一下。

#include <iostream>#include <cstdio>#include <cstdlib>#include <cstring>using namespace std;__int64 n,q;__int64 num[100100];char c[10];__int64 x,y,z,ans;struct PPP{       __int64 l,r,sum,lazy;}tree[210000];__int64 tail;void build(__int64 k,__int64 s,__int64 t){       tree[k].lazy=0;       __int64 mid = (s+t)/2;       if (s == t) {                    tree[k].sum = num[s];                    return;                   }       tail++;       tree[k].l = tail;       build(tail,s,mid);       tail++;       tree[k].r = tail;       build(tail,mid+1,t);       tree[k].sum = tree[tree[k].l].sum+tree[tree[k].r].sum;       return;}//求某一段数的和 __int64 find(__int64 s,__int64 t,__int64 k,__int64 ss,__int64 tt){    __int64 mid = (ss+tt)/2;    if (ss != tt) {                   tree[tree[k].l].lazy += tree[k].lazy;                   tree[tree[k].r].lazy += tree[k].lazy;                  }    tree[k].sum += (tt-ss+1) * tree[k].lazy;    tree[k].lazy = 0;    if (s==ss&&t==tt) {                       return tree[k].sum;                      }    if (s>=mid+1){                  return find(s,t,tree[k].r,mid+1,tt);                 }    if (t<=mid)  {                  return find(s,t,tree[k].l,ss,mid);                 }    return find(s,mid,tree[k].l,ss,mid)+find(mid+1,t,tree[k].r,mid+1,tt);}//改变某段数的值 void change(__int64 s,__int64 t,__int64 k,__int64 ss,__int64 tt,__int64 temp){     __int64 mid = (ss+tt)/2;     if (ss != tt) {                    tree[tree[k].l].lazy += tree[k].lazy;                    tree[tree[k].r].lazy += tree[k].lazy;                   }     tree[k].sum += (tt-ss+1) * tree[k].lazy;     tree[k].lazy = 0;     if (s==ss&&t==tt) {                        tree[k].lazy += temp;                        return;                       }                  else {                        tree[k].sum += (t-s+1) * temp;                       }     if (s>=mid+1){                   change(s,t,tree[k].r,mid+1,tt,temp);                   return;                  }     if (t<=mid)  {                   change(s,t,tree[k].l,ss,mid,temp);                   return;                  }     change(s,mid,tree[k].l,ss,mid,temp);     change(mid+1,t,tree[k].r,mid+1,tt,temp);     return;}//查找某一个数的值 void work(__int64 k,__int64 s,__int64 t){     __int64 mid = (s+t)/2;     if (s == t) {                  //printf("!!!!%I64d %I64d\n",s,tree[k].sum+tree[k].lazy);                  return;                 }     work(tree[k].l,s,mid);     work(tree[k].r,mid+1,t);}int main(){    scanf("%I64d%I64d",&n,&q);    for (__int64 i = 1; i <= n  ; i ++)        scanf("%I64d",&num[i]);    tail = 1;    build(1,1,n);    for (__int64 i = 1 ; i <= q ; i ++)    {        scanf("%s",c);        if (c[0] == 'Q') {                          scanf("%I64d%I64d",&x,&y);                          ans = find(x,y,1,1,n);                          printf("%I64d\n",ans);                         }        if (c[0] == 'C') {                          scanf("%I64d%I64d%I64d",&x,&y,&z);                          change(x,y,1,1,n,z);                         }    }    //system("pause");    return 0;}


原创粉丝点击