解题思路:此题就是树状数组求最大值的模版题。按照实际效果树状数组比线段树的时间更少些~编程复杂度更小。
Problem : 1754 ( I Hate It ) Judge Status : Accepted
RunId : 7538799 Language : G++ Author : CherryChou
Code Render Status : Rendered By HDOJ G++ Code Render Version 0.01 Beta
RunId : 7538799 Language : G++ Author : CherryChou
Code Render Status : Rendered By HDOJ G++ Code Render Version 0.01 Beta
#include<iostream> #include<cstdio> #include<cstring> #include<string> #include<algorithm> using namespace std; int n; int a[200010],p[200010];//a是树状数组 int lowb(int t) {return t&(-t);} void init(){//找最大值初始化 for(int i=1;i<=n;i++){ a[i]=p[i]; for(int j=1;j<lowb(i);j<<=1)//找比i小的数但又在lowbit(i)+1到i这个区间上的数更新p数组 a[i]=max(a[i],a[i-j]);//j是以2倍的速度增长 } } void add(int i,int v){ p[i]=v; while(i<=n){ if(v>a[i]) a[i]=v; else break; i+=lowb(i); } } int getmax(int l,int r){//找最大值 int ans=p[r]; while(1){ ans=max(ans,p[r]);//跟r位置上的数字比较 if(l==r) break; for(r=r-1;r-l>=lowb(r);r-=lowb(r)){//尼玛 1 跟 L 没分清囧了。。。 if(ans<a[r]) ans=a[r]; } }//r自减1,判断r-lowbit(r)和l之间的关系如果l在区间内就不能减了而是继续循环 return ans;//如果l比r-lowbit(r)小的话,就可以之间判断ans和p[r]的最值了 } int main(){ int m,i,maxx,id,sd; char ch[2]; while(~scanf("%d%d",&n,&m)){ memset(a,0,sizeof(a)); for(i=1;i<=n;i++) scanf("%d",&p[i]); init(); for(i=1;i<=m;i++){ scanf("%s%d%d",ch,&id,&sd); if(ch[0]=='Q'){ maxx=getmax(id,sd); printf("%d\n",maxx); } else if(ch[0]=='U'){ add(id,sd); } } } return 0; }
每天都在一点一点的进步!