hdu1754

来源:互联网 发布:平面设计三大软件 编辑:程序博客网 时间:2024/06/09 19:10

做这题目之前,只是听说过线段树可以解决求解最大值(最小值)的题目,到了这题,也不得不设法解决。但是建树的代码出了错,一直不能执行,

知道午睡之后,再看代码,觉得缺了什么,然后看了下书,建树错了。

其实线段树的mid一直是tree[v].l+tree[v].r的二分之一.

题目比较简单,没啥可说的:

#include<stdio.h>
#include<iostream>
using namespace std;
const int N=200010;
struct node
{
     int value,l,r;
};
node tree[4000000];
int a[N];
int max(int x,int y)
{
     return (x>y)?x:y;
}
void build(int v,int l,int r)
{
     tree[v].l=l,tree[v].r=r;//一开始建树,没有给这个参数,然后就坏了
     if(l==r)
     {
          tree[v].value=a[r];
          return ;
     }
     int mid=(l+r)/2;
     build(v*2,l,mid);
     build(v*2+1,mid+1,r);
     tree[v].value=max(tree[v*2].value,tree[v*2+1].value);
     return ;
}
void update(int v,int A,int temp)
{
     if(tree[v].l==A&&tree[v].r==A){
          tree[v].value=temp;
          return ;
     }
     tree[v].value=max(tree[v].value,temp);//每个子树都有被改变的可能
     int mid=(tree[v].l+tree[v].r)/2;
     if(A<=mid)
          update(v*2,A,temp);//单个节点的更新,每次只能落入两子树中的一个
     else
          update(v*2+1,A,temp);
     return;
}
int query(int v,int l,int r)
{
     if(tree[v].l==l&&tree[v].r==r)
          return tree[v].value;
     if(tree[v].l==tree[v].r)
          return tree[v].value;
     int mid=(tree[v].l+tree[v].r)/2;
     if(r<=mid)
          return query(v*2,l,r);
     else if(l>mid)
          return query(v*2+1,l,r);
     else
     {
          int sum1=query(v*2,l,mid);
          int sum2=query(v*2+1,mid+1,r);
          return max(sum1,sum2);
     }
}
int main()
{
     int n,m,A,B;
     char str;
     while(~scanf("%d%d",&n,&m))
     {
          for(int i=1;i<=n;i++)
               scanf("%d",&a[i]);
          build(1,1,n);
          for(int j=1;j<=m;j++){
               getchar();
               scanf("%c%d%d",&str,&A,&B);
               if(str=='U')
               {
                    update(1,A,B);
                    a[A]=B;
               }
               if(str=='Q')
                    printf("%d\n",query(1,A,B));
          }
     }
     return 0;
}

0 0
原创粉丝点击