4487. Can you answer these queries VI
Problem code: GSS6
Given a sequence A of N (N <= 100000) integers, you have to apply Q (Q <= 100000) operations:Insert, delete, replace an element, find the maximum contiguous(non empty) sum in a given interval.
Input
The first line of the input contains an integer N.The following line contains N integers, representing the startingsequence A1..AN, (|Ai| <= 10000).The third line contains an integer Q. The next Q lines contains the operations in following form:I x y: insert element y at position x (between x - 1 and x).D x : delete the element at position x.R x y: replace element at position x with y.Q x y: print max{Ai + Ai+1 + .. + Aj | x <= i <= j <= y}.All given positions are valid, and given values are between -10000 and +10000.The sequence will never be empty.
Output
For each "Q" operation, print an integer(one per line) as described above.
Example
Input:53 -4 3 -1 610I 6 2Q 3 5R 5 -4Q 3 5D 2Q 1 5I 2 -10Q 1 6R 2 -1Q 1 6Output:83635
第二次写splay居然遇上了考splay的常数优化。弄了很久。首先是读入优化,貌似SPOJ上面数据有'\r'所以要特殊判断。然后inline所有函数,最后把splay移到一个struct里面会加速很多。
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<ctime>
#include<cmath>
#include<algorithm>
#include<
set>
#include<map>
#include<vector>
#include<
string>
#include<queue>
using namespace std;
#ifdef WIN32
#define LL "%I64d"
#else
#define LL "%lld"
#endif
#define MAXN 110000
#define MAXV MAXN*2
#define MAXE MAXV*2
#define MAXT MAXN*2
#define INF 0x3f3f3f3f
#define INFL 0x3f3f3f3f3f3f3f3fLL
#define lch splay[now].ch[0]
#define rch splay[now].ch[1]
typedef long long qword;
inline int nextInt()
{
char ch;
int x=
0;
bool flag=
false;
do
ch=(
char)getchar(),flag=(ch==
'-')?
true:flag;
while(ch<
'0'||ch>
'9');
do x=x*
10+ch-
'0';
while (ch=(
char)getchar(),ch<=
'9' && ch>=
'0');
return x*(flag?-
1:
1);
}
int n,m;
int root=
0,topt=
0;;
struct sss
{
int lx,rx,mx,val,sum,siz,pnt;
int ch[
2];
}splay[MAXT];
inline void up(
int now)
{
splay[now].lx=splay[now].rx=splay[now].mx=-
INF;
if (lch)splay[now].lx=
max(splay[now].lx,splay[lch].lx);
splay[now].lx=max(splay[now].lx,max(splay[lch].sum+splay[now].val,splay[lch].sum+splay[now].val+
splay[rch].lx));
if (rch)splay[now].rx=
max(splay[now].rx,splay[rch].rx);
splay[now].rx=max(splay[now].rx,max(splay[rch].sum+splay[now].val,splay[rch].sum+splay[now].val+
splay[lch].rx));
splay[now].mx=
splay[now].val;
if (lch)splay[now].mx=
max(splay[now].mx,splay[lch].mx);
if (rch)splay[now].mx=
max(splay[now].mx,splay[rch].mx);
splay[now].mx=max(splay[now].mx,splay[lch].rx+splay[rch].lx+
splay[now].val);
splay[now].mx=max(splay[now].mx,splay[rch].lx+
splay[now].val);
splay[now].mx=max(splay[now].mx,splay[lch].rx+
splay[now].val);
splay[now].siz=splay[lch].siz+splay[rch].siz+
1;
splay[now].sum=splay[lch].sum+splay[rch].sum+
splay[now].val;
}
inline void Rotate(
int now)
{
int p=splay[now].pnt,anc=
splay[p].pnt;
int dir=splay[p].ch[
0]==
now;
if (anc)
splay[anc].ch[splay[anc].ch[1]==p]=
now;
splay[now].pnt=
anc;
splay[splay[now].ch[dir]].pnt=
p;
splay[p].ch[1-dir]=
splay[now].ch[dir];
splay[p].pnt=
now;
splay[now].ch[dir]=
p;
up(p);
up(now);
}
/*
inline int Get_kth(int now,int rk)
{
if (rk==siz[splay[now].ch[0]]+1)
return now;
if (rk<siz[splay[now].ch[0]]+1)
return Get_kth(splay[now].ch[0],rk);
else
return Get_kth(splay[now].ch[1],rk-siz[splay[now].ch[0]]-1);
}*/
inline int Get_kth(
int rk)
{
int now=
root;
while (rk!=splay[splay[now].ch[
0]].siz+
1)
{
if (rk>splay[splay[now].ch[
0]].siz+
1)
{
rk-=splay[splay[now].ch[
0]].siz+
1;
now=splay[now].ch[
1];
}else
{
now=splay[now].ch[
0];
}
}
return now;
}
inline void Splay(
int now,
int tp=
0)
{
if (now==tp)
return ;
while (splay[now].pnt!=
tp)
{
int p=splay[now].pnt,anc=
splay[p].pnt;
if (anc==
tp)
Rotate(now);
else if( (splay[anc].ch[
0]==p) == (splay[p].ch[
0]==
now))
{
Rotate(p);
Rotate(now);
}else
{
Rotate(now);
Rotate(now);
}
}
if (tp==
0)root=
now;
}
inline void Insert(
int pos,
int v)
{
int now=++
topt;
splay[now].ch[0]=splay[now].ch[
1]=
0;
splay[now].pnt=
0;
splay[now].val=
v;
splay[now].siz=
1;
splay[now].lx=splay[now].rx=splay[now].mx=splay[now].sum=
v;
if (!
pos)
{
Splay(Get_kth(1));
splay[now].ch[1]=
root;
splay[root].pnt=
now;
root=
now;
up(now);
return ;
}
Splay(Get_kth(pos));
splay[now].pnt=
root;
splay[now].ch[1]=splay[root].ch[
1];
splay[splay[root].ch[1]].pnt=
now;
splay[root].ch[1]=
now;
up(now);
up(root);
return ;
}
inline void Delete(
int pos)
{
Splay(Get_kth(pos));
if (pos!=
splay[root].siz)
{
Splay(Get_kth(pos+
1),root);
/**/
splay[splay[root].ch[1]].ch[
0]=splay[root].ch[
0];
splay[splay[root].ch[0]].pnt=splay[root].ch[
1];;
splay[splay[root].ch[1]].pnt=
splay[root].pnt;
root=splay[root].ch[
1];
}else
{
root=splay[root].ch[
0];
splay[root].pnt=
0;
}
up(root);
}
inline int Qry_mxs(
int l,
int r)
{
if (l==
1 && r==
splay[root].siz)
{
return splay[root].mx;
}else if (l==
1)
{
Splay(Get_kth(r+
1));
return splay[splay[root].ch[
0]].mx;
}else if (r==
splay[root].siz)
{
Splay(Get_kth(l-
1));
return splay[splay[root].ch[
1]].mx;
}else
{
Splay(Get_kth(l-
1));
Splay(Get_kth(r+
1),root);
return splay[splay[splay[root].ch[
1]].ch[
0]].mx;
}
}
inline void Chg_val(
int pos,
int v)
{
Splay(Get_kth(pos));
splay[root].val=
v;
up(root);
}
void Scan(
int now)
{
if (!now)
return ;
if (splay[now].siz!=splay[lch].siz+splay[rch].siz+
1)
throw 2;
if (splay[now].ch[
0])
{
if (splay[splay[now].ch[
0]].pnt!=now)
throw 1;
Scan(splay[now].ch[0]);
}
printf("%d ",splay[now].val);
if (splay[now].ch[
1])
{
if (splay[splay[now].ch[
1]].pnt!=now)
throw 1;
Scan(splay[now].ch[1]);
}
}
void Build_tree(
int &now,
int *num,
int l,
int r)
{
now=++
topt;
int mid=(l+r)>>
1;
splay[now].siz=
1;
splay[now].sum=splay[now].val=splay[now].mx=splay[now].lx=splay[now].rx=
num[mid];
if (l<=mid-
1)Build_tree(lch,num,l,mid-
1);
if (mid+
1<=r)Build_tree(rch,num,mid+
1,r);
splay[lch].pnt=
now;
splay[rch].pnt=
now;
up(now);
}
int num[MAXN];
int main()
{
freopen("input.txt",
"r",stdin);
//freopen("output.txt","w",stdout);
int i,j,k;
int x,y,z;
scanf("%d",&
n);
for (i=
0;i<n;i++
)
{
x=
nextInt();
num[i]=
x;
}
Build_tree(root,num,0,n-
1);
scanf("%d\n",&
m);
char opt;
for (i=
0;i<m;i++
)
{
opt=
getchar();
//scanf("%c",&opt);
if (opt==
'I')
{
// scanf("%d%d",&x,&y);
x=nextInt();y=
nextInt();
x--
;
Insert(x,y);
}else if (opt==
'Q')
{
// scanf("%d%d",&x,&y);
x=nextInt();y=
nextInt();
printf("%d\n",Qry_mxs(x,y));
}else if (opt==
'R')
{
// scanf("%d%d",&x,&y);
x=nextInt();y=
nextInt();
Chg_val(x,y);
}else if (opt==
'D')
{
// scanf("%d",&x);
x=
nextInt();
Delete(x);
}
getchar();
}
return 0;
}
转载于:https://www.cnblogs.com/mhy12345/p/4029533.html