JuQueen

題目來源:http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=134851

 輸入:

10 10 5
state 0
groupchange 2 9 7
state 9
groupchange 0 2 10
change 0 -5
輸出:

0
7
7
3
-3

題意:

   輸入:n,top,Q (1<=n<=4587520,1<=top<=1000,1<=Q<=50000)
   n爲10個初值爲0的數,top是最大限制(後面會提),Q,操作數。
  state:0 當前0下標,數值是多少。輸出
   groupchange : 2 9 7 更新區間[2,9] 的值,最多加7,和不能大於top。輸出能加的值。
  change:0 -5 下標爲0的數,最多加-5,結果不能<0;輸出能加的值。

思路:線段樹,更新查找。(維護區間最大值最小值)
 
<pre name="code" class="cpp">#include<iostream>
#include<cstdio>
#include<cstring>
#define maxn 5000000
#define INF 1147483648
using namespace std;

int max(int x,int y) {return x>y?x:y;}
int min(int x,int y) {return x<y?x:y;}
int mmax,mmin;
struct data
{
 int l,r,minv,maxv,cover,add;
}tree[4*maxn];


void build(int u,int L,int R)
{
     tree[u].l = L; tree[u].r=R;
     tree[u].add=0;
     tree[u].cover=0;
     tree[u].minv=0;
     tree[u].maxv=0;
     if(L==R) return;
     int M=(R+L)/2;
      build(u<<1,L,M);
      build((u<<1)+1,M+1,R);
    tree[u].minv=min(tree[u<<1].minv, tree[(u<<1)+1].minv);
    tree[u].maxv=max(tree[u<<1].maxv, tree[(u<<1)+1].maxv);

}

void get_down(int u)
{
        tree[u<<1].minv+=tree[u].add;
        tree[u<<1].maxv+=tree[u].add;
        tree[u<<1].add+=tree[u].add;
        tree[u<<1].cover=1;

        tree[(u<<1)+1].minv+=tree[u].add;
        tree[(u<<1)+1].maxv+=tree[u].add;
        tree[(u<<1)+1].add+=tree[u].add;
        tree[(u<<1)+1].cover=1;

        tree[u].cover=0;
        tree[u].add=0;
}
void update(int u,int ql,int qr,int v)
{

    if(tree[u].l==ql&&tree[u].r==qr)
    {
       tree[u].minv+=v;
       tree[u].maxv+=v;
       tree[u].add+=v;
       tree[u].cover=1;
       return ;
    }
     int mid=(tree[u].l+tree[u].r)/2;
     if(qr<=mid)
           update(u<<1,ql,qr,v);
       else if(ql>= mid+1)
          update((u<<1)+1,ql,qr,v);
      else
       {
        update(u<<1,ql,mid,v);
        update((u<<1)+1,mid+1,qr,v);
       }
//需要維護父親節點
    tree[u].minv=min(tree[u<<1].minv, tree[(u<<1)+1].minv);
    tree[u].maxv=max(tree[u<<1].maxv, tree[(u<<1)+1].maxv);
}

void query(int u,int ql,int qr)
{
    if(tree[u].l==ql&&tree[u].r==qr)
    {
        mmax=max(mmax,tree[u].maxv);
        mmin=min(mmin,tree[u].minv);
        return ;
    }
     if(tree[u].cover)
      get_down(u);
       int mid=(tree[u].l+tree[u].r)/2;
      if(qr<=mid)
           query(u<<1,ql,qr);
       else if(ql>=mid+1)
          query((u<<1)+1,ql,qr);
      else
       {
        query(u<<1,ql,mid);
        query((u<<1)+1,mid+1,qr);
       }
}

int main()
{
    int n,top,Q;
    char str[100];
    int a,b,x;
    while(scanf("%d%d%d",&n,&top,&Q)!=EOF)
    {
         build(1,1,n);
         while(Q--)
         {

             scanf("%s",str);
             if(str[0]=='s')
             {
                 scanf("%d",&a);
                 a++;
                  mmax=0; mmin=INF;
                 query(1,a,a);
                 printf("%d\n",mmin);
             }
             if(str[0]=='g')
             {
                 scanf("%d%d%d",&a,&b,&x);
                 a++;b++;
                  mmax=0; mmin=INF;
                 query(1,a,b);
                 if(x<=0)
                 {
                    if(x+mmin<0)
                    {
                        int t=mmin*-1;
                        update(1,a,b,t);
                        printf("%d\n",t);
                    }
                    else
                    {
                        update(1,a,b,x);
                        printf("%d\n",x);
                    }
                 }
                 else
                 {
                     if(mmax+x>top)
                     {
                         int t=top-mmax;
                         update(1,a,b,t);
                         printf("%d\n",t);
                     }
                     else
                     {
                         update(1,a,b,x);
                         printf("%d\n",x);
                     }
                 }
             }
             if(str[0]=='c')
             {
                 scanf("%d%d",&a,&x);
                 a++;
                  mmax=0; mmin=INF;
                 query(1,a,a);
                 if(x<=0)
                 {
                     if(x+mmin<0)
                     {
                         int t=-1*mmin;
                         update(1,a,a,t);
                         printf("%d\n",t);
                     }
                     else
                     {
                         update(1,a,a,x);
                         printf("%d\n",x);
                     }
                 }
                 else
                 {
                     if(x+mmax>top)
                     {
                         int t=top-mmax;
                         update(1,a,a,t);
                         printf("%d\n",t);
                     }
                     else
                     {
                         update(1,a,a,x);
                         printf("%d\n",x);
                     }
                 }
             }
         }
    }
 return 0;
}



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章