I Hate ItTime Limit: 9000/3000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 98898 Accepted Submission(s): 37261 Problem Description 很多学校流行一种比较的习惯。老师们很喜欢询问,从某某到某某当中,分数最高的是多少。 Input 本题目包含多组测试,请处理到文件结束。 Output 对于每一次询问操作,在一行里面输出最高成绩。 Sample Input 5 6 1 2 3 4 5 Q 1 5 U 3 6 Q 3 4 Q 4 5 U 2 9 Q 1 5 Sample Output 5 6 5 9 |
在成功的路上了!!!加油
AC代码:
#include <bits/stdc++.h>
using namespace std;
const int MAXN = 1<<19;
const int MAXu = 2e6+10;
int father[MAXu];
struct node{
int value;
int left;
int right;
}tree[MAXN];
void BuildTree(int i,int left,int right){ //建树,从上往下建
tree[i].left = left;
tree[i].right = right;
tree[i].value = 0;
if(left == right){
father[left] = i;
return ;
}
BuildTree((i<<1),left,(int)(floor(left+right)/2.0)); //左树
BuildTree((i<<1)+1,(int)(floor(left+right)/2.0)+1,right);//右树
}
void UpdateTree(int tr){
if(tr == 1){ // 等于根退出操作 ,自底向上更新
return ;
}
int fa = tr/2;
int a = tree[fa<<1].value; // 父节点的左子树的最大值
int b = tree[(fa<<1)+1].value; //父节点的右子树的最大值 << 优先级小于+
tree[fa].value = max(a,b);
UpdateTree(tr/2);
}
int Maxt;
void Query(int i,int l,int r){ //查找
if(tree[i].left == l && tree[i].right == r){
Maxt = max(Maxt,tree[i].value);
return ;
}
i = (i<<1);
if(l <= tree[i].right){ //还是有点没明白
if(r <= tree[i].right) Query(i,l,r);
else Query(i,l,tree[i].right);
}
i++;
if(r >= tree[i].left){
if(l >= tree[i].left) Query(i,l,r);
else Query(i,tree[i].left,r);
}
}
int main()
{
int n,m,g;
int a,b;
char ch;
while(scanf("%d%d",&n,&m)==2){
BuildTree(1,1,n);
for(int i=1;i<=n;i++){
scanf("%d",&g);
tree[father[i]].value = g;
UpdateTree(father[i]);
}
while(m--){
getchar();
scanf("%c%d%d",&ch,&a,&b);
if(ch=='Q'){
Maxt = 0; //初始化最大值
Query(1,a,b); //进行查找
printf("%d\n",Maxt);
}
else{
tree[father[a]].value = b;
UpdateTree(father[a]); //更新
}
}
}
return 0;
}