您的位置:首页 > 其它

[NOI2004]郁闷的出纳员

2011-04-17 09:14 429 查看

[NOI2004]郁闷的出纳员

一个基本的sbt,开始太傻了,居然在删除人的时候我一个一个的去删,还以为很快,结果毫无悬念TLE。其实删除的时候只要T[t].key<mi了,那么就直接把整棵树都删掉

要知道有多少个人被开除了,直接tol-T[root].size

/*
* File:   main.cpp
* Author: Mi
*
* Created on 2011年4月14日, 下午9:13
*/
#include <stdio.h>
#include <string.h>
#include <algorithm>
#define N 100005
using namespace std;
/*
*
*/
int tol,sum,mi;
struct SBT
{
int left,right;
int key;
int size;
void init()
{
left=right=0;
size=1;
}
}T
;
void R_Rotate(int &t)
{
int k=T[t].left;
T[t].left=T[k].right;
T[k].right=t;
T[k].size=T[t].size;
T[t].size=T[T[t].left].size+T[T[t].right].size+1;
t=k;
return ;
}
void L_Rotate(int &t)
{
int k=T[t].right;
T[t].right=T[k].left;
T[k].left=t;
T[k].size=T[t].size;
T[t].size=T[T[t].left].size+T[T[t].right].size+1;
t=k;
return ;
}
void Maintain(int &t,bool flag)
{
if(flag==false)
{
if(T[T[T[t].left].left].size>T[T[t].right].size)
R_Rotate(t);
else if(T[T[T[t].left].right].size>T[T[t].right].size)
{
L_Rotate(T[t].left);
R_Rotate(t);
}
else
return ;
}
else
{
if(T[T[T[t].right].right].size>T[T[t].left].size)
L_Rotate(t);
else if(T[T[T[t].right].left].size>T[T[t].left].size)
{
R_Rotate(T[t].right);
L_Rotate(t);
}
else
return ;
}
Maintain(T[t].left,false);
Maintain(T[t].right,true);
Maintain(t,false);
Maintain(t,true);
}
void Insert(int &t,int v)//鎻掑叆
{
if(t==0)
{
t=++tol;
T[t].init();
T[t].key=v;
}
else
{
T[t].size++;
if(v<T[t].key)
Insert(T[t].left,v);
else
Insert(T[t].right,v);
Maintain(t,v>=T[t].key);
}
}
/*int Delete(int &t,int v)//鍒犻櫎
{
if(!t)
return 0;
T[t].size--;
if(v==T[t].key||v<T[t].key&&!T[t].left||v>T[t].key&&!T[t].right)
{
if(T[t].left&&T[t].right)
{
int p=Delete(T[t].left,v+1);
T[t].key=T[p].key;
return p;
}
else
{
int p=t;
t=T[t].left+T[t].right;
return p;
}
}
else
return Delete(v<T[t].key?T[t].left:T[t].right,v);
}*/
void Delete(int &t)//删除是删除比mi小的整个一颗子树
{
if(!t)
return ;
if(T[t].key+sum>=mi)
{
Delete(T[t].left);
T[t].size=T[T[t].left].size+T[T[t].right].size+1;
}
else
{
t=T[t].right;
Delete(t);
}
}
int Find_k(int t,int k)
{
if(k<=T[T[t].left].size)
return Find_k(T[t].left,k);
else if(k>T[T[t].left].size+1)
return Find_k(T[t].right,k-T[T[t].left].size-1);
return T[t].key;
}
int Getmax(int t)
{
while(T[t].right)
t=T[t].right;
return t;
}
int Getmi(int t)
{
while(T[t].left)
t=T[t].left;
return t;
}
int main(int argc, char** argv)
{
int n;
int root=0;
tol=0;
sum=0;
scanf("%d%d",&n,&mi);
while(n--)
{
char str[2];
int p;
scanf("%s%d",str,&p);
if(str[0]=='I')
{
if(p>=mi)
Insert(root,p-sum);
}
else if(str[0]=='S')
{
sum-=p;
Delete(root);
}
else if(str[0]=='A')
sum+=p;
else if(str[0]=='F')
{
if(p>T[root].size)
puts("-1");
else
printf("%d/n",Find_k(root,T[root].size-p+1)+sum);
}
}
printf("%d/n",tol-T[root].size);
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: