Dijkstra--The Captain
给定平面上的n个点,定义$(x_1,y_1)$到$(x_2,y_2)$的费用为min(|$x_1$-$x_2$|,|$y_1$-$y_2$|),求从1号点走到n号点的最小费用。
先给一段证明:给定三个x值,$x_1<x_2<x_3$。可得$x_2-x_1<x_3-x_2<x_3-x_1$,对于最小费用,很明显只有$x_2-x_1$是有用的。对y同理,同时要注意我们不能把$x$和$y$两者混谈。由此我们得到了一个思路,分层图x和y跑一次最短路。
首先两个$cmp$函数对$n$个点进行的两次排序(注意在之前把点的序号也存下来):
bool cmp1(node a,node b)
{
return a.x<b.x;
}
bool cmp2(node a,node b)
{
return a.y<b.y;
}
链式前向星构图:
struct edge
{
int next,to,w;
}edge[maxn];
void add(int u,int v,int w)
{
edge[++tot].w=w;
edge[tot].to=v;
edge[tot].next=head[u];
head[u]=tot;
}
sort(a+,a+n+,cmp1);
for (int i = ;i < n;i++)
{
add(a[i].id,a[i+].id,abs(a[i].x-a[i+].x));
add(a[i+].id,a[i].id,abs(a[i].x-a[i+].x));
}
sort(a+,a+n+,cmp2);
for (int i = ;i < n;i++)
{
add(a[i].id,a[i+].id,abs(a[i].y-a[i+].y));
add(a[i+].id,a[i].id,abs(a[i].y-a[i+].y));
}
然后是很标准的dij板子:
void Dijkstra(int S)
{
q.push(make_pair(,S)); memset(vis,,sizeof(vis)); memset(dis,0x3f,sizeof(dis)); dis[S] = ;
while(!q.empty())
{
int x = q.top().second;
q.pop();
if(vis[x])
continue;
vis[x] = ;
for(int i=head[x];i!=;i=edge[i].next)
{
int to1=edge[i].to;
if(dis[to1] > dis[x] + edge[i].w)
{
dis[to1] = dis[x] + edge[i].w ;
q.push(make_pair(-dis[to1],to1));
}
}
}
return;
}
完整代码如下:
#include <iostream>
#include <algorithm>
#include <cstdio>
#include <cstring>
#include <queue>
#include <cmath>
using namespace std;
#define ll long long
int n;
const int maxn=;
priority_queue< pair<int ,int > >q;
int dis[maxn],vis[maxn];
int tot=,head[maxn];
int read(){
int x=,a=;
char ch=getchar();
while (ch < ''||ch > ''){
if (ch == '-') x=-;
ch = getchar();
}
while (ch <= ''&&ch >= '')
{
a = a* + ch- '';
ch=getchar();
}
return x*a;
}
struct node
{
int x,y,id;
}a[maxn];
struct edge
{
int next,to,w;
}edge[maxn];
void add(int u,int v,int w)
{
edge[++tot].w=w;
edge[tot].to=v;
edge[tot].next=head[u];
head[u]=tot;
}
bool cmp1(node a,node b)
{
return a.x<b.x;
}
bool cmp2(node a,node b)
{
return a.y<b.y;
}
void Dijkstra(int S)
{
q.push(make_pair(,S)); memset(vis,,sizeof(vis)); memset(dis,0x3f,sizeof(dis)); dis[S] = ;
while(!q.empty())
{
int x = q.top().second;
q.pop();
if(vis[x])
continue;
vis[x] = ;
for(int i=head[x];i!=;i=edge[i].next)
{
int to1=edge[i].to;
if(dis[to1] > dis[x] + edge[i].w)
{
dis[to1] = dis[x] + edge[i].w ;
q.push(make_pair(-dis[to1],to1));
}
}
}
return;
}
int main()
{
n=read();
for (int i = ;i <= n;i++)
{
a[i].x=read(),a[i].y=read();
a[i].id=i;
}
sort(a+,a+n+,cmp1);
for (int i = ;i < n;i++)
{
add(a[i].id,a[i+].id,abs(a[i].x-a[i+].x));
add(a[i+].id,a[i].id,abs(a[i].x-a[i+].x));
}
sort(a+,a+n+,cmp2);
for (int i = ;i < n;i++)
{
add(a[i].id,a[i+].id,abs(a[i].y-a[i+].y));
add(a[i+].id,a[i].id,abs(a[i].y-a[i+].y));
}
Dijkstra();
cout<<dis[n];
return ;
}
Dijkstra--The Captain的更多相关文章
- BZOJ4152The Captain[DIjkstra]
4152: [AMPPZ2014]The Captain Time Limit: 20 Sec Memory Limit: 256 MBSubmit: 700 Solved: 266[Submit ...
- 循环队列+堆优化dijkstra最短路 BZOJ 4152: [AMPPZ2014]The Captain
循环队列基础知识 1.循环队列需要几个参数来确定 循环队列需要2个参数,front和rear 2.循环队列各个参数的含义 (1)队列初始化时,front和rear值都为零: (2)当队列不为空时,fr ...
- bzoj4152 The Captain (dijkstra)
做dijkstra,但只需要贪心地把每个点连到它左边.右边.上边.下面的第一个点就可以了 #include<bits/stdc++.h> #define pa pair<int,in ...
- 【bzoj4152】[AMPPZ2014]The Captain 堆优化Dijkstra
题目描述 给定平面上的n个点,定义(x1,y1)到(x2,y2)的费用为min(|x1-x2|,|y1-y2|),求从1号点走到n号点的最小费用. 输入 第一行包含一个正整数n(2<=n< ...
- BZOJ4152 The Captain(dijkstra+巧妙建图)
BZOJ4152 The Captain 题面很简洁: 给定平面上的n个点,定义(x1,y1)到(x2,y2)的费用为min(|x1-x2|,|y1-y2|),求从1号点走到n号点的最小费用. 很明显 ...
- BZOJ 4152: [AMPPZ2014]The Captain Dijkstra+贪心
Code: #include <queue> #include <cstdio> #include <cstring> #include <algorithm ...
- 【堆优化Dijkstra】BZOJ4152- [AMPPZ2014]The Captain
[题目大意] 给定平面上的n个点,定义(x1,y1)到(x2,y2)的费用为min(|x1-x2|,|y1-y2|),求从1号点走到n号点的最小费用. [思路] 按照某维坐标排序,相邻两个点在这一维度 ...
- BZOJ 4152: [AMPPZ2014]The Captain( 最短路 )
先按x排序, 然后只有相邻节点的边才有用, 我们连起来, 再按y排序做相同操作...然后就dijkstra ---------------------------------------------- ...
- bzoj4152[AMPPZ2014]The Captain 最短路
4152: [AMPPZ2014]The Captain Time Limit: 20 Sec Memory Limit: 256 MBSubmit: 1517 Solved: 603[Submi ...
- 『The Captain 最短路建图优化』
The Captain(BZOJ 4152) Description 给定平面上的n个点,定义(x1,y1)到(x2,y2)的费用为min(|x1-x2|,|y1-y2|),求从1号点走到n号点的最小 ...
随机推荐
- 隐患写法flag.equals("true")带来的空指针异常
分类:2008-06-04 12:47 467人阅读 评论(0) 收藏 举报 linuxjava测试 昨天,有同事A对同事B写的程序进行测试时,出现错误,看控制台信息,发现抛出了空指针异常. 调查结果 ...
- python-python基础3
本章内容: 函数 递归 高阶函数 一.函数 一个函数一般完成一项特定的功能 函数使用 函数需要先定义 使用函数,调用
- NO31 配置网卡--主机名--网络故障排查面试题--DNS
修改网卡配置信息: 修改主机名规范的三个步骤: 配置默认网关: DNS解析过程,用命令看: DNS相关命令: 口述DNS解析过程: 客户端(电脑)通过浏览器输入域名,先找hosts文件及本地dns缓 ...
- STM32学习笔记:IIC通信协议详解(附带软件模拟源码)
什么是IIC(I2C)? IIC 即Inter-Integrated Circuit(集成电路总线),这种总线类型是由飞利浦半导体公司设计出来的一种简单.双向.二线制.同步串行总线.它是一种多向控制总 ...
- 外网如何访问 Service?【转】
除了 Cluster 内部可以访问 Service,很多情况我们也希望应用的 Service 能够暴露给 Cluster 外部.Kubernetes 提供了多种类型的 Service,默认是 Clus ...
- Elasticsearch学习入门
一.关于Elasticsearch 1.特点 Elasticsearch基于全文搜索引擎 Apache Lucene ,由Java开发而来,面向API进行搜索, Restful 风格,分布式文件存储. ...
- MySQL 中的数据库名称、数据表名称、字段名称
如何查询Oracle,Sql Server,MySQL 中的数据库名称.数据表名称.字段名称 分类: Database2012-09-24 22:16 7034人阅读 评论(0) 收藏 举报 数据库s ...
- 我的第一个爬虫【python selenium】
去年写的一个小功能,一年过得好快,好快! 目的:爬取京东商品详情页面的内容(商品名称.价格.评价数量)后存储到xls文档中,方便商家分析自己商品的动态. 软件:chrome(windows).chro ...
- eclipse环境变量设置
eclipse的运行需要java,但是当安装了多个版本的jdk后,eclipse可能就不能用了. 解决办法就是: #eclipse 文件夹下有eclipse.ini配置文件,在文件首行添加如下信息: ...
- 038、Java中逻辑运算之非运算“!”
01.代码如下: package TIANPAN; /** * 此处为文档注释 * * @author 田攀 微信382477247 */ public class TestDemo { public ...