BZOJ 1604 [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居 Treap
题意:链接
方法: Treap
解析:
前几道资格赛的题水的不行,这道Gold的题就够分量辣。
首先这个曼哈顿距离啥的肯定能做文章,怎么转化是个问题,自己玩了一会没玩出来,就查了查曼哈顿距离的转化,发现这个玩意转化之后就变得有思路多了,所以这数学本领还是非常重要啊=-=
先看曼哈顿距离的定义
|x1−x2|+|y1−y2|
拆绝对值
x1−x2+y1−y2或x1−x2+y2−y1
x2−x1+y1−y2或x2−x1+y2−y1
即|x1+y1−(x2+y2)|或|x1−y1−(x2−y2)|
设x1+y1为x′,x1−y1为y′
则|x1′−x2′|或|y1′−y2′|
所以原要求1转化为
max(|x1′−x2′|,|y1′−y2′|)<=c
这样的二维的东西显然排序一下降一维。
按x’排序后。维护一个x’的队列,再对y’维护一个平衡树即可了。
至于要求2,即是并查集,也就是说平衡树每一次拿出来前驱后继维护下并查集即可。
y’显然可能反复,又维护并查集我们须要拿出来标号。所以平衡树须要多维护一个no,所以再删除的时候我们要找到v与no都跟要删除的目标节点同样的节点删除。
(前驱写挫WA一次= =!
代码:
#include <ctime>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <algorithm>
#define N 100010
using namespace std;
int fa[N];
int q[N];
int tot;
int root;
int cnt[N];
struct node
{
int l,r,w,v,no,rnd,siz;
}tr[N];
void pushup(int rt)
{
tr[rt].siz=tr[tr[rt].l].siz+tr[tr[rt].r].siz+tr[rt].w;
}
void rturn(int &rt)
{
int t=tr[rt].l;
tr[rt].l=tr[t].r;
tr[t].r=rt;
tr[t].siz=tr[rt].siz;
pushup(rt);
rt=t;
}
void lturn(int &rt)
{
int t=tr[rt].r;
tr[rt].r=tr[t].l;
tr[t].l=rt;
tr[t].siz=tr[rt].siz;
pushup(rt);
rt=t;
}
void insert(int &rt,int v,int no)
{
if(!rt)
{
rt=++tot;
tr[rt].siz=1,tr[rt].no=no,tr[rt].rnd=rand();
tr[rt].v=v,tr[rt].w=1;
return;
}
tr[rt].siz++;
if(v<=tr[rt].v)
{
insert(tr[rt].l,v,no);
if(tr[tr[rt].l].rnd<tr[rt].rnd)rturn(rt);
}else
{
insert(tr[rt].r,v,no);
if(tr[tr[rt].r].rnd<tr[rt].rnd)lturn(rt);
}
}
void del(int &rt,int v,int no)
{
if(!rt)return;
tr[rt].siz--;
if(tr[rt].v==v&&tr[rt].no==no)
{
if(tr[rt].l*tr[rt].r==0){rt=tr[rt].l+tr[rt].r;return;}
else
{
if(tr[tr[rt].l].rnd<tr[tr[rt].r].rnd)
{
rturn(rt);
del(rt,v,no);
}else
{
lturn(rt);
del(rt,v,no);
}
}
}else if(v<tr[rt].v)
{
del(tr[rt].l,v,no);
}else del(tr[rt].r,v,no);
}
int ans;
void q_pre(int rt,int v)
{
if(!rt)return;
if(v>=tr[rt].v)
{
ans=rt;
q_pre(tr[rt].r,v);
}else q_pre(tr[rt].l,v);
}
void q_sub(int rt,int v)
{
if(!rt)return;
if(v<tr[rt].v)
{
ans=rt;
q_sub(tr[rt].l,v);
}else q_sub(tr[rt].r,v);
}
struct point
{
int x,y;
}pt[N];
int n,c;
int find(int x)
{
if(x!=fa[x])return fa[x]=find(fa[x]);
return x;
}
int cmp(point a,point b)
{
if(a.x==b.x)return a.y<b.y;
return a.x<b.x;
}
int main()
{
scanf("%d%d",&n,&c);
for(int i=1;i<=n;i++)
{
int x,y;
scanf("%d%d",&x,&y);
pt[i].x=x+y,pt[i].y=x-y;
fa[i]=i;
}
sort(pt+1,pt+n+1,cmp);
int head=1,tail=0;
for(int i=1;i<=n;i++)
{
while(head<=tail&&pt[i].x-pt[q[head]].x>c)
{
del(root,pt[q[head]].y,q[head]);
head++;
}
ans=0;
q_pre(root,pt[i].y);
int tmp=ans;
if(tmp!=0)
{
if(pt[i].y-tr[tmp].v<=c)
{
if(find(i)!=find(tr[tmp].no))
{
fa[find(i)]=find(tr[tmp].no);
}
}
}
ans=0;
q_sub(root,pt[i].y);
tmp=ans;
if(tmp!=0)
{
if(tr[tmp].v-pt[i].y<=c)
{
if(find(i)!=find(tr[tmp].no))
{
fa[find(i)]=find(tr[tmp].no);
}
}
}
insert(root,pt[i].y,i);
q[++tail]=i;
}
int ma=0,print=0;
for(int i=1;i<=n;i++)
{
int fx=find(i);
if(!cnt[fx])
{
print++;
}
cnt[fx]++;
if(cnt[fx]>ma)ma=cnt[fx];
}
printf("%d %d\n",print,ma);
}
BZOJ 1604 [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居 Treap的更多相关文章
- BZOJ 1604: [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居
题目 1604: [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居 Time Limit: 5 Sec Memory Limit: 64 MB Description ...
- bzoj 1604 [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居(set+并查集)
Description 了解奶牛们的人都知道,奶牛喜欢成群结队.观察约翰的N(1≤N≤100000)只奶牛,你会发现她们已经结成了几个“群”.每只奶牛在吃草的 时候有一个独一无二的位置坐标Xi,Yi( ...
- bzoj 1604: [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居——排序+贪心+set
Description 了解奶牛们的人都知道,奶牛喜欢成群结队.观察约翰的N(1≤N≤100000)只奶牛,你会发现她们已经结成了几个“群”.每只奶牛在吃草的时候有一个独一无二的位置坐标Xi,Yi(l ...
- BZOJ 1604 [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居:队列 + multiset + 并查集【曼哈顿距离变形】
题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=1604 题意: 平面直角坐标系中,有n个点(n <= 100000,坐标范围10^9) ...
- bzoj 1604: [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居 曼哈顿生成树
大致题意:统计平面上由曼哈顿距离小于等于c的点对组成联通块的个数. 曼哈顿生成树的模板题.有关讲解:http://blog.csdn.net/acm_cxlove/article/details/88 ...
- bzoj 1604: [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居【切比雪夫距离+并查集+multiset】
参考:http://hzwer.com/4361.html 坐标开long long,inf开大点 先曼哈顿转切比雪夫(x+y,x-y),距离就变成了max(x',y'): 先按x排序,维护两个指针, ...
- 【BZOJ1604】[Usaco2008 Open]Cow Neighborhoods 奶牛的邻居 Treap+并查集
[BZOJ1604][Usaco2008 Open]Cow Neighborhoods 奶牛的邻居 Description 了解奶牛们的人都知道,奶牛喜欢成群结队.观察约翰的N(1≤N≤100000) ...
- 【BZOJ】1604: [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居(set+并查集+特殊的技巧)
http://www.lydsy.com/JudgeOnline/problem.php?id=1604 这题太神了... 简直就是 神思想+神做法+神stl.. 被stl整的我想cry...首先,, ...
- 【BZOJ】1604: [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居
[算法]并查集+平衡树+数学+扫描线 [题解] 经典曼哈顿距离转切比雪夫距离. 曼哈顿距离:S=|x1-x2|+|y1-y2|<=c 即:max(x1-x2+y1-y2,x1-x2-y1+y2, ...
随机推荐
- 运行npm start vue.js项目 出现 npm ERR! missing script: start 错误
npm ERR! missing script: start 错误 有可能缺少依赖包,运行nmp install安装依赖(一般都依赖很多包,过程有点慢),安装完后发现多一个 node_modules文 ...
- [HNOI2004]高精度开根
题目:洛谷P2293.BZOJ1213. 题目大意:给你$n,k(n\leq 10^{10000},k\leq 50)$,求$\lfloor \sqrt[k]{n}\rfloor$. 解题思路:高精度 ...
- [转载][来自csdn]RTS和CTS是什么意思?
原文链接: http://blog.csdn.net/zmq5411/article/details/6280332 这篇文章看着挺好,明白易懂,顺手转过来 34RTS和CTS是什么意思? 解释一:R ...
- vue-router 实现无效路由(404)的友好提示
最近在做一个基于vue-router的SPA,想对无效路由(404)页面做下统一处理.这次我真的没有在官方文档找到具体的说明[捂脸]所以本文仅是我DIY的一个思路,求轻虐=_= 在我的理解中,vue- ...
- centos6.5_x86_64 下安装 Oracle11gR2 的详细过程
也可参考:http://blog.csdn.net/nhm_lxy/article/details/37813789 转自:http://www.cnblogs.com/pengineer/p/435 ...
- 【Codeforces Round #420 (Div. 2) C】Okabe and Boxes
[题目链接]:http://codeforces.com/contest/821/problem/C [题意] 给你2*n个操作; 包括把1..n中的某一个数压入栈顶,以及把栈顶元素弹出; 保证压入和 ...
- 分布式文件存储FastDFS(一)初识FastDFS
一.FastDFS简单介绍 FastDFS是一款开源的.分布式文件系统(Distributed File System),由淘宝开发平台部资深架构师余庆开发.作为一个分布式文件系统,它对文件进行管理. ...
- oracle之ROWNUM的查询应用
1 在ORACLE数据库中,ROWNUM是ORACLE数据库为查询结果加入的一个伪列.起始值为1.经常使用来处理查询结果的分页. 2 因为ROWNUM的特殊性,使用时候一般是分三层: 第一层:先进行查 ...
- ubuntu12.04更新软件源时出现校验和不符
在运行update命令之后.出现系统校验和不符.网上找了一些方法,最后在大神的帮助下最终攻克了! ! 1.更改 /etc/apt/apt.conf.d/00aptitude 文件,在最后一行增加: A ...
- .net framework tools
https://docs.microsoft.com/en-us/dotnet/framework/tools/ Resgen.exe (Resource File Generator) Conver ...