题意:

给你平面上的$n$个点,共有$m$个弹跳装置。

每个弹跳装置可以从点$p_{i}$以$t_{i}$的代价跳到矩形$(L_{i},D_{i}),(R_{i},U_{i})$中的任何一个点。

现在请你对于每座城市求出从1号点跳到它的最小代价。

$n\leq 70000,m\leq 150000$。

题解:不把边建出来的$KD-tree$优化建图。

看一眼就知道$KD-tree$优化建图,但如果把所有边都建出来就爆炸了。

设原图上的点是实点,$KD-tree$上的点(代表一个实点和一个矩形)是虚点。

那么在$Dijkstra$到每个点的时候:

  • 若是实点,在$KD-tree$上查找能连的虚点/实点并向其连带权边。
  • 若是虚点,向它的两个儿子和它对应的实点连权为0的边。

时间复杂度$O(m\sqrt{n})$,空间复杂度$O(m\sqrt{n})$(实际上只有优先队列可能达到这个空间,其他都是$O(n)$)。

没了。不知道为什么有人写线段树。

代码:

#include<bits/stdc++.h>
#define maxn 200005
#define maxm 500005
#define inf 0x7fffffff
#define ll long long
#define rint register int
#define debug(x) cerr<<#x<<": "<<x<<endl
#define fgx cerr<<"--------------"<<endl
#define dgx cerr<<"=============="<<endl using namespace std;
struct Point{int x[],iid;}p[maxn];
int mx[maxn][],mn[maxn][],id[maxn],ls[maxn],rs[maxn];
int tot,np,dis[maxn<<],vis[maxn<<],tim[maxn];
int L[maxn],R[maxn],D[maxn],U[maxn];
struct node{int u,d;bool operator<(const node &b)const{return d>b.d;}};
priority_queue<node> q; vector<int> vc[maxn]; inline int read(){
int x=,f=; char c=getchar();
for(;!isdigit(c);c=getchar()) if(c=='-') f=-;
for(;isdigit(c);c=getchar()) x=x*+c-'';
return x*f;
} inline node md(int u,int d){node res;res.u=u,res.d=d;return res;}
inline void upd(int u,int v){if(dis[u]>v){dis[u]=v,q.push(md(u,v));}}
inline bool ok(int xa,int ya,int xb,int yb){return xb<=xa&&ya<=yb;}
inline bool cmp(Point a,Point b){return (!np)?(a.x[]<b.x[]):(a.x[]<b.x[]);}
inline void pushup(int k){
for(rint i=;i<;i++){
mx[k][i]=mn[k][i]=p[id[k]].x[i];
if(ls[k]) mx[k][i]=max(mx[k][i],mx[ls[k]][i]),mn[k][i]=min(mn[k][i],mn[ls[k]][i]);
if(rs[k]) mx[k][i]=max(mx[k][i],mx[rs[k]][i]),mn[k][i]=min(mn[k][i],mn[rs[k]][i]);
}
}
inline int build(int l,int r,int type){
if(l>r) return ;
int mid=l+r>>,k=++tot;
id[k]=mid,np=type;
nth_element(p+l,p+mid,p+r+,cmp);
ls[k]=build(l,mid-,type^);
rs[k]=build(mid+,r,type^);
pushup(k); return k;
}
inline void add(int l,int r,int d,int u,int c,int k){
if(mx[k][]<l || mn[k][]>r || mx[k][]<d || mn[k][]>u) return;
if(ok(mn[k][],mx[k][],l,r)&&ok(mn[k][],mx[k][],d,u)){upd(k,c);return;}
if(ok(p[id[k]].x[],p[id[k]].x[],l,r)&&ok(p[id[k]].x[],p[id[k]].x[],d,u)) upd(p[id[k]].iid,c);
if(ls[k]) add(l,r,d,u,c,ls[k]); if(rs[k]) add(l,r,d,u,c,rs[k]);
} inline void Dijkstra(int s,int n){
memset(vis,,sizeof(vis));
memset(dis,,sizeof(dis));
dis[s]=,q.push(md(s,));
while(!q.empty()){
rint u=q.top().u; q.pop();
if(vis[u]) continue; vis[u]=;
if(u<=n) for(rint i=;i<vc[u].size();i++)
add(L[vc[u][i]],R[vc[u][i]],D[vc[u][i]],U[vc[u][i]],dis[u]+tim[vc[u][i]],n+);
else upd(p[id[u]].iid,dis[u]),upd(ls[u],dis[u]),upd(rs[u],dis[u]);
}
} int main(){
freopen("jump.in","r",stdin);
freopen("jump.out","w",stdout);
int n=read(),m=read(),w=read(),h=read();
for(rint i=;i<=n;i++)
p[i].x[]=read(),p[i].x[]=read(),p[i].iid=i;
tot=n,build(,n,);
for(rint i=;i<=m;i++){
int p=read();tim[i]=read();
L[i]=read(),R[i]=read();
D[i]=read(),U[i]=read();
vc[p].push_back(i);
}
Dijkstra(,n);
for(rint i=;i<=n;i++) printf("%d\n",dis[i]);
return ;
}

D2T1

[NOI2019] 弹跳的更多相关文章

  1. 【题解】Luogu P5471 [NOI2019]弹跳

    原题传送门 先考虑部分分做法: subtask1: 暴力\(O(nm)\)枚举,跑最短路 subtask2: 吧一行的点压到vector中并排序,二分查找每一个弹跳装置珂以到达的城市,跑最短路 sub ...

  2. 洛谷 P5471 - [NOI2019] 弹跳(二维线段树优化建图+堆优化存边)

    题面传送门 一道非常有意思的题(大概可以这么形容?) 首先看到这类一个点想一个区域内连边的题目可以很自然地想到线段树优化建图,只不过这道题是二维的,因此需要使用二维线段树优化建图,具体来说,我们外层开 ...

  3. [NOI2019]弹跳(KD-Tree/四分树/线段树套平衡树 优化建图+Dijkstra)

    本题可以用的方法很多,除去以下三种我所知道的就还有至少三种. 方法一:类似线段树优化建图,将一个平面等分成四份(若只有一行或一列则等分成两份),然后跑Dijkstra即可.建树是$O(n\log n) ...

  4. luogu P5471 [NOI2019]弹跳

    luogu 因为是一个点向矩形区域连边,所以可以二维数据结构优化连边,但是会MLE.关于维护矩形的数据结构还有\(KD-Tree\),所以考虑\(KDT\)优化连边,空间复杂度\(m\sqrt n\) ...

  5. luogu 5471 [NOI2019]弹跳 KDtree + Dijkstra

    题目链接 第一眼就是 $KDtree$ 优化建图然而,空间只有 $128mb$,开不下   时间不吃紧,考虑直接跑 $Dijkstra$ $Dijkstra$ 中存储的是起点到每个输入时给出的矩阵的最 ...

  6. p5471 [NOI2019]弹跳

    分析 代码 #include<bits/stdc++.h> using namespace std; #define fi first #define se second #define ...

  7. [NOI2019]弹跳(KD-Tree)

    被jump送退役了,很生气. 不过切了这题也进不了队,行吧. 退役后写了一下,看到二维平面应该就是KD树,然后可以在KD树上做最短路,然后建立堆和KDTree.然后每次更新则是直接把最短路上的节点删掉 ...

  8. 题解 [NOI2019]弹跳

    题目传送门 题目大意 给出 \(n\) 做城市,每座城市都有横纵坐标 \(x,y\).现在给出 \(m\) 个限制 \(p,t,l,r,d,u\),表示从 \(p\) 城市出发,可以花费 \(t\) ...

  9. 【NOI2019】弹跳(KDT优化建图)

    Description 平面上有 \(n\) 个点,分布在 \(w \times h\) 的网格上.有 \(m\) 个弹跳装置,由一个六元组描述.第 \(i\) 个装置有参数:\((p_i, t_i, ...

随机推荐

  1. npm install 报错 -4048

    方法1: 删除npmrc文件. 强调:不是nodejs安装目录npm模块下的那个npmrc文件,而是在C:\Users\{账户}\下的.npmrc文件. 方法2: https://www.jiansh ...

  2. ROW_NUMBER()实现分页

    1. 在数据表基础上面添加一个自增的一列记录行数(虚拟的实际数据库不存在,不会影响数据库结构)的列当然也顺便起一个别名(我这里起了一个rowNum) 2.由于rowNum是一个虚拟的.若直接使用会报' ...

  3. gradle入门

    gradle入门 简介: Gradle是一个基于Apache Ant和Apache Maven概念的项目自动化构建开源工具.它使用一种基于Groovy的特定领域语言(DSL)来声明项目设置,抛弃了基于 ...

  4. <人人都懂设计模式>-单例模式

    这个模式,我还是了解的. 书上用了三种不同的方法. class Singleton1: # 单例实现方式1 __instance = None __is_first_init = False def ...

  5. visual studio之X64调试问题

    这个问题没有解决. 只能X86啦!

  6. jmeter压测学习8-压测带token的接口

    前言 工作中我们需要压测的接口大部分都是需要先登陆后,带着token的接口(或者带着cookies),我们可以先登陆获取token再关联到下个接口. 比如我现在要压测一个修改用户的个人信息接口,每个用 ...

  7. jmeter压测学习5-XPath提取器

    前言 有些web项目是前后端不分离的,返回的内容不是那种纯进口返回json格式,返回的是一个HTML页面. 并且有些参数是隐藏在html里面的,需要先从html页面中取出隐藏参数,如:csrfmidd ...

  8. 初识V4l2(二)-------浅析video_register_device

    在V4l2初识(一)中,我们已经知道当插上一个摄像头的时候,在uvc_driver.c中最终会调用函数video_register_device函数.接下来我们就简要分析这个函数做了哪些事情,揭开其神 ...

  9. PoI 3.17 已过时代码对比

    PoI 3.17 已过时代码对比颜色定义变化旧版本 : HSSFColor.BLACK.index新版本 : IndexedColors.BLACK.index 获取单元格格式旧版本 : cell.g ...

  10. 201871010128-杨丽霞《面向对象程序设计(Java)》第十二周学习总结

    201871010128-杨丽霞<面向对象程序设计(Java)>第十一周学习总结 项目 内容 这个作业属于哪个课程 https://www.cnblogs.com/nwnu-daizh/ ...