HDU 1754 I Hate It(线段树单点更改、区间查找最大值)
生活随笔
收集整理的這篇文章主要介紹了
HDU 1754 I Hate It(线段树单点更改、区间查找最大值)
小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
Problem Description 很多學(xué)校流行一種比較的習(xí)慣。老師們很喜歡詢問(wèn),從某某到某某當(dāng)中,分?jǐn)?shù)最高的是多少。
這讓很多學(xué)生很反感。
不管你喜不喜歡,現(xiàn)在需要你做的是,就是按照老師的要求,寫一個(gè)程序,模擬老師的詢問(wèn)。當(dāng)然,老師有時(shí)候需要更新某位同學(xué)的成績(jī)。
在每個(gè)測(cè)試的第一行,有兩個(gè)正整數(shù) N 和 M ( 0<N<=200000,0<M<5000 ),分別代表學(xué)生的數(shù)目和操作的數(shù)目。
學(xué)生ID編號(hào)分別從1編到N。
第二行包含N個(gè)整數(shù),代表這N個(gè)學(xué)生的初始成績(jī),其中第i個(gè)數(shù)代表ID為i的學(xué)生的成績(jī)。
接下來(lái)有M行。每一行有一個(gè)字符 C (只取'Q'或'U') ,和兩個(gè)正整數(shù)A,B。
當(dāng)C為'Q'的時(shí)候,表示這是一條詢問(wèn)操作,它詢問(wèn)ID從A到B(包括A,B)的學(xué)生當(dāng)中,成績(jī)最高的是多少。
當(dāng)C為'U'的時(shí)候,表示這是一條更新操作,要求把ID為A的學(xué)生的成績(jī)更改為B。
這讓很多學(xué)生很反感。
不管你喜不喜歡,現(xiàn)在需要你做的是,就是按照老師的要求,寫一個(gè)程序,模擬老師的詢問(wèn)。當(dāng)然,老師有時(shí)候需要更新某位同學(xué)的成績(jī)。
?
Input 本題目包含多組測(cè)試,請(qǐng)?zhí)幚淼轿募Y(jié)束。在每個(gè)測(cè)試的第一行,有兩個(gè)正整數(shù) N 和 M ( 0<N<=200000,0<M<5000 ),分別代表學(xué)生的數(shù)目和操作的數(shù)目。
學(xué)生ID編號(hào)分別從1編到N。
第二行包含N個(gè)整數(shù),代表這N個(gè)學(xué)生的初始成績(jī),其中第i個(gè)數(shù)代表ID為i的學(xué)生的成績(jī)。
接下來(lái)有M行。每一行有一個(gè)字符 C (只取'Q'或'U') ,和兩個(gè)正整數(shù)A,B。
當(dāng)C為'Q'的時(shí)候,表示這是一條詢問(wèn)操作,它詢問(wèn)ID從A到B(包括A,B)的學(xué)生當(dāng)中,成績(jī)最高的是多少。
當(dāng)C為'U'的時(shí)候,表示這是一條更新操作,要求把ID為A的學(xué)生的成績(jī)更改為B。
?
Output 對(duì)于每一次詢問(wèn)操作,在一行里面輸出最高成績(jī)。?
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 Hint Huge input,the C function scanf() will work better than cin?
Author linle?
Source 2007省賽集訓(xùn)隊(duì)練習(xí)賽(6)_linle專場(chǎng) #include <cstdio> #include <iostream> #include <cmath> #include <string> #include <cstring> #include <algorithm> #include <queue> #include <vector> #include <map> using namespace std;#define ll long long #define eps 1e-9const int inf = 0x3f3f3f3f; const int mod = 1e9+7;int n, m, ans, a[2000000+8], x, y; char c;struct node {int l, r, sum; }tree[4*2000000+8];void build(int i, int l, int r)///建樹 {tree[i].sum = 0;tree[i].l = l;tree[i].r = r;if(l == r)///如果是葉子節(jié)點(diǎn) {tree[i].sum = a[l];///則讓它的值存進(jìn)去return ;}int mid = (tree[i].r+tree[i].l)/2;///如果不是葉子節(jié)點(diǎn)build(i*2, l, mid);///搜索左兒子的區(qū)間build(i*2+1, mid+1, r);///搜索右兒子的區(qū)間tree[i].sum = max(tree[i*2].sum , tree[i*2+1].sum);///使該區(qū)間最大的值往上傳 }void pls(int i, int pos, int k)///單點(diǎn)改變 {if(tree[i].r == pos && tree[i].l == tree[i].r)///如果時(shí)所要尋找的葉子節(jié)點(diǎn) {tree[i].sum = k;///改變?cè)擖c(diǎn)的值return ;}int mid = (tree[i].l+tree[i].r)/2;if(pos <= mid)///如果位置在左邊,就往左邊找pls(i*2, pos, k);else///否則往右邊找pls(i*2+1, pos, k);tree[i].sum = max(tree[i*2].sum , tree[i*2+1].sum);///不斷更新父親節(jié)點(diǎn)的最大值 }void search(int i, int l, int r) {if(tree[i].l >= l && tree[i].r <= r){ans = max(ans, tree[i].sum);return;}int mid = (tree[i].l+tree[i].r)/2;if(l <= mid)search(i*2, l, r);///區(qū)間不能寫成search(i*2, pos, k),因?yàn)檫@樣區(qū)間會(huì)改變,但是題目要求要查的是[l, r]之間的最大值if(mid < r)search(i*2+1, l, r); }int main() {while(~scanf("%d%d", &n, &m) && (n+m)){for(int i = 1; i <= n; i++)scanf("%d", &a[i]);build(1, 1, n);for(int i = 1; i <= m; i++){ans = -1;getchar();scanf("%c %d %d", &c, &x, &y);if(c == 'Q'){search(1, x, y);printf("%d\n", ans);}else if(c == 'U'){pls(1, x, y);}}}return 0; }?
轉(zhuǎn)載于:https://www.cnblogs.com/RootVount/p/11302748.html
總結(jié)
以上是生活随笔為你收集整理的HDU 1754 I Hate It(线段树单点更改、区间查找最大值)的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 用维基百科训练word2vec中文词向量
- 下一篇: 后缀数组DC3算法实现