题意:线段树操作:1. 单点更新 2. 求区间的LCIS(longest consecutive increasing subsequence)
分析:注意是连续的子序列,就是简单的区间合并,记录线段的端点的值,如果rx[rt<<1] < lx[rt<<1|1]就区间合并,最后结果保存在ms中。因为记录的数据较多,索性结构体内再开一个结构体,感觉还不错。写完这题,对区间合并的操作有了更深的理解。
/************************************************
* Author :Running_Time
* Created Time :2015/9/25 星期五 10:37:34
* File Name :G.cpp
************************************************/
#include <cstdio>
#include <algorithm>
#include <iostream>
#include <sstream>
#include <cstring>
#include <cmath>
#include <string>
#include <vector>
#include <queue>
#include <deque>
#include <stack>
#include <list>
#include <map>
#include <set>
#include <bitset>
#include <cstdlib>
#include <ctime>
using namespace std;
#define lson l, mid, rt << 1
#define rson mid + 1, r, rt << 1 | 1
typedef long long ll;
const int N = 1e5 + 10;
const int INF = 0x3f3f3f3f;
const int MOD = 1e9 + 7;
const double EPS = 1e-8;
struct ST {
struct Node {
int lx, rx;
int ls, rs, ms;
}node[N<<2];
void push_up(int l, int r, int rt) {
node[rt].ls = node[rt<<1].ls; node[rt].rs = node[rt<<1|1].rs;
node[rt].lx = node[rt<<1].lx; node[rt].rx = node[rt<<1|1].rx;
node[rt].ms = max (node[rt<<1].ms, node[rt<<1|1].ms);
int mid = (l + r) >> 1;
if (node[rt<<1].rx < node[rt<<1|1].lx) {
if (node[rt<<1].ls == mid - l + 1) {
node[rt].ls += node[rt<<1|1].ls;
}
if (node[rt<<1|1].rs == r - mid) {
node[rt].rs += node[rt<<1].rs;
}
node[rt].ms = max (node[rt].ms, node[rt<<1].rs + node[rt<<1|1].ls);
}
}
void build(int l, int r, int rt) {
if (l == r) {
scanf ("%d", &node[rt].lx);
node[rt].rx = node[rt].lx;
node[rt].ls = node[rt].rs = node[rt].ms = 1;
return ;
}
int mid = (l + r) >> 1;
build (lson); build (rson);
push_up (l, r, rt);
}
void updata(int p, int c, int l, int r, int rt) {
if (l == r) {
node[rt].lx = node[rt].rx = c; return ;
}
int mid = (l + r) >> 1;
if (p <= mid) updata (p, c, lson);
else updata (p, c, rson);
push_up (l, r, rt);
}
int query(int ql, int qr, int l, int r, int rt) {
if (ql <= l && r <= qr) {
return node[rt].ms;
}
int mid = (l + r) >> 1, ret = 0;
if (ql <= mid) {
ret = max (ret, query (ql, qr, lson));
}
if (qr > mid) {
ret = max (ret, query (ql, qr, rson));
}
if (node[rt<<1].rx < node[rt<<1|1].lx) {
ret = max (ret, min (mid - ql + 1, node[rt<<1].rs) + min (qr - mid, node[rt<<1|1].ls));
}
return ret;
}
}st;
int main(void) {
int T; scanf ("%d", &T);
while (T--) {
int n, q; scanf ("%d%d", &n, &q);
st.build (1, n, 1);
for (int a, b, i=1; i<=q; ++i) {
char s[2]; scanf ("%s%d%d", &s, &a, &b);
if (s[0] == ‘Q‘) {
printf ("%d\n", st.query (a + 1, b + 1, 1, n, 1));
}
else {
st.updata (a + 1, b, 1, n, 1);
}
}
}
return 0;
}
原文:http://www.cnblogs.com/Running-Time/p/4837805.html