题意:一家宠物收养所负责处理领养者与遗弃宠物业务,有人来领宠物,则领一只最理想的。若没有宠物了,领养者们就得等到宠物来,宠物一来立刻送给其中一个等待者。如果有两个理想的选择,则选择那个值较小的。收养所时刻只存在人or宠物or没有存在任何!

思路:

  这题主要是树中可能存在人或者宠物,但两者不可能同时存在,因为一旦存在,必须有对象被配对并从树中删除。 所有函数独自写起来都是很简单的,但是合起来使用时就得小心了,得配合一点。

  要时刻注意树中是否还有节点,若没有,则可能要树要换种类了。

 #include <bits/stdc++.h>
#define pii pair<int,int>
#define INF 0x3f7f7f7f
#define LL long long
using namespace std;
const int N=;
const int mod=; struct node
{
int key, pre, ch[];
}nod[N];
int node_cnt, root, flag; int create_node(int v,int far)
{
nod[node_cnt].ch[]=nod[node_cnt].ch[]=;
nod[node_cnt].pre=far;
nod[node_cnt].key=v;
return node_cnt++;
} void Rotate(int t,int d)
{
int son=nod[t].ch[d];
int far=nod[t].pre;
int gra=nod[far].pre;
nod[t].pre=gra;
nod[far].pre=t;
nod[son].pre=far;
nod[t].ch[d]=far;
nod[far].ch[d^]=son;
nod[gra].ch[ nod[gra].ch[]==far ]=t;
} int Insert(int t,int v)
{
if(t==) return root=create_node(v, ); //树中还没有节点。
if( v < nod[t].key )
{
if(nod[t].ch[]) return Insert(nod[t].ch[], v);
else return nod[t].ch[]=create_node(v, t);
}
else
{
if(nod[t].ch[]) return Insert(nod[t].ch[], v);
else return nod[t].ch[]=create_node(v, t);
}
} void Splay(int t, int goal)
{
while(nod[t].pre!=goal)
{
int f=nod[t].pre, g=nod[f].pre;
if(g==goal) Rotate( t, nod[f].ch[]==t );
else
{
int d1=nod[f].ch[]==t, d2=nod[g].ch[]==f;
if(d1==d2) Rotate(f, d1),Rotate(t, d1);
else Rotate(t, d1),Rotate(t, d2);
}
}
if(goal==) root=t; //随时更新根!
} int Find(int t,int v) //在子树t中找到值为v的点,返回点号
{
while(t)
{
if(v==nod[t].key) return t;
if(v<nod[t].key) t=nod[t].ch[];
else t=nod[t].ch[];
}
return ; //找不到
} int Find_pre(int t,int v)
{
int val=-;
while(t)
{
if(nod[t].key<v) val=max(val, nod[t].key);
if(v<nod[t].key) t=nod[t].ch[];
else t=nod[t].ch[];
}
if(val<) return INF;
return val;
} int Find_bac(int t,int v)
{
int val=INF;
while(t)
{
if(nod[t].key>v) val=min(val, nod[t].key);
if(v<nod[t].key) t=nod[t].ch[];
else t=nod[t].ch[];
}
return val;
} void Delete(int v) //在树中删除值为v的任意一个点
{
Splay(Find(root, v), ); //将目标旋转到根
int L=nod[root].ch[];
int R=nod[root].ch[];
if(L== && R==) root=;
else if(R==) //没有右子树
{
nod[L].pre=;
root=L;
}
else if(L==) //没有左子树
{
nod[R].pre=;
root=R;
}
else //有前有后
{
while(nod[R].ch[]) R=nod[R].ch[]; //找到后继
Splay(R, root);
nod[R].ch[]=L;
nod[R].pre=;
nod[L].pre=R;
root=R;
}
} int main()
{
//freopen("input.txt", "r", stdin);
int n, ans, a, b, contain;
while(cin>>n)
{
flag=node_cnt=;
contain=root=ans=;
while(n--)
{
scanf("%d%d",&a,&b);
if(a==flag || contain==) // 树为空 or 树中是同种类 则 插入
{
flag=a;
contain++;
Splay(Insert(root, b), );
}
else
{
if(Find(root, b)) Delete(b); //刚好有值为b的。
else
{
int L=Find_pre(root, b);
int R=Find_bac(root, b);
if( abs(L-b)<=abs(R-b) ) //L和R不可能同时为INF。
{
ans=(ans+abs(L-b))%mod;
Delete(L);
}
else
{
ans=(ans+abs(R-b))%mod;
Delete(R);
}
}
contain--;
}
}
printf("%d\n", ans );
}
return ;
}

AC代码

HYSBZ 1208 宠物收养所 (Splay树)的更多相关文章

  1. bzoj 1208 宠物收养所--splay

    这个题也是单点维护,不管来的是人还是狗,只要num=0就插入,否则就删除. // File Name: ACM/bzoj/1208.cpp // Author: Zlbing // Created T ...

  2. BZOJ 1208 宠物收养所 | 平衡树模板题

    BZOJ 1208 宠物收养所 我犯过的错误:删除一个节点后没有update新的根节点,导致size错了! #include <cstdio> #include <cmath> ...

  3. Bzoj 1208: [HNOI2004]宠物收养所(splay)

    1208: [HNOI2004]宠物收养所 Time Limit: 10 Sec Memory Limit: 162 MB Description 最近,阿Q开了一间宠物收养所.收养所提供两种服务:收 ...

  4. 【BZOJ-1208】宠物收养所 Splay

    1208: [HNOI2004]宠物收养所 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 6638  Solved: 2601[Submit][Sta ...

  5. 【BZOJ1208】[HNOI2004]宠物收养所 Splay

    还是模板题,两颗splay,找点删即可. #include <iostream> #include <cstdio> #include <cstdlib> #def ...

  6. BZOJ 1208 宠物收养所

    Description 最近,阿Q开了一间宠物收养所.收养所提供两种服务:收养被主人遗弃的宠物和让新的主人领养这些宠物.每个领养者都希望领养到自己满意的宠物,阿Q根据领养者的要求通过他自己发明的一个特 ...

  7. BZOJ 1208 宠物收养所 set+二分

    题目链接: https://www.lydsy.com/JudgeOnline/problem.php?id=1208 题目大意: 最近,阿Q开了一间宠物收养所.收养所提供两种服务:收养被主人遗弃的宠 ...

  8. [bzoj1208][HNOI2004]宠物收养所——splay

    题目大意 Description 最近,阿Q开了一间宠物收养所.收养所提供两种服务:收养被主人遗弃的宠物和让新的主人领养这些宠物.每个领养者都希望领养到自己满意的宠物,阿Q根据领养者的要求通过他自己发 ...

  9. HNOI2004宠物收养所(splay维护二叉搜索树模板题)

    描述 最近,阿Q开了一间宠物收养所.收养所提供两种服务:收养被主人遗弃的宠物和让新的主人领养这些宠物.每个领养者都希望领养到自己满意的宠物,阿Q根据领养者的要求通过他自己发明的一个特殊的公式,得出该领 ...

随机推荐

  1. codeforces 459E E. Pashmak and Graph(dp+sort)

    题目链接: E. Pashmak and Graph time limit per test 1 second memory limit per test 256 megabytes input st ...

  2. UVA-11082 Matrix Decompressing(有上下界的最大流)

    题目链接: Matrix Decompressing 题意: 给一个矩阵的每行和每列的和,(给的是前i行或者列的和); 矩阵中每个元素的值在1到20之间,找出这样的一个矩阵: 思路: 把它转化成一个二 ...

  3. Dijkstra堆优化

    Dijkstra是一个非常不错的最短路算法,它使用两层循环进行枚举,通过每次更新蓝白点的方式更新最短路,时间复杂度为O(n^2),优于floyd的O(n^3),不过只能用于计算单源最短路,而且无法处理 ...

  4. limit的用法

    limit子句可以用于强制select语句返回指定的记录数.limit接受一个或两个数字参数,参数必须是整数常量.如果给定两个参数,第一个参数指定第一个返回记录行的偏移量,第二个参数指定返回记录行的最 ...

  5. Bootstrap-CSS:代码

    ylbtech-Bootstrap-CSS:代码 1.返回顶部 1. Bootstrap 代码 Bootstrap 允许您以两种方式显示代码: 第一种是 <code> 标签.如果您想要内联 ...

  6. JavaScript-Tool:wdtree

    ylbtech-JavaScript-Tool:wdtree 1.返回顶部 1. 插件描述:wdTree是一个轻量级jQuery插件用于创建一个带有嵌套Check Boxe的树形控件. wdTree是 ...

  7. ASP.NET Core MVC 2.x 全面教程_ASP.NET Core MVC 21. Model 验证 Again

    深入的将Model验证 手动添加验证的错误 view里面显示每个属性的验证错误信息 显示整个model级别错误 自定义验证 如果业务逻辑需要比较复杂的验证.而且这个验证逻辑可能到处复用的话就应该考虑使 ...

  8. H.264(MPEG-4 AVC)级别(Level)、DPB 与 MaxDpbMbs 详解(转载)

    转自:http://www.cnblogs.com/zyl910/archive/2011/12/08/h264_level.html 对于H.264(MPEG-4 AVC)而言,级别(Level)是 ...

  9. 洛谷 - P1004 - 方格取数 - 简单dp

    https://www.luogu.org/problemnew/show/P1004 这道题分类到简单dp但是感觉一点都不简单……这种做两次的dp真的不是很懂怎么写.假如是贪心做两次,感觉又不能证明 ...

  10. 51nod 1138 【数学-等差数列】

    思路: 很显然每个连续的序列都是等差数列, 那么我们利用等差数列求和公式. S=(a1+a1+k-1)k/2=(2·a1+k-1)*k/2;a1是首项,k是个数. 枚举k,首项最小为1,k最大,具体不 ...