POJ_1556_The Doors_判断线段相交+最短路
POJ_1556_The Doors_判断线段相交+最短路
Description

Input
2
4 2 7 8 9
7 3 4.5 6 7
The first line contains the number of interior walls. Then there is a
line for each such wall, containing five real numbers. The first number
is the x coordinate of the wall (0 < x < 10), and the remaining
four are the y coordinates of the ends of the doorways in that wall. The
x coordinates of the walls are in increasing order, and within each
line the y coordinates are in increasing order. The input file will
contain at least one such set of data. The end of the data comes when
the number of walls is -1.
Output
output should contain one line of output for each chamber. The line
should contain the minimal path length rounded to two decimal places
past the decimal point, and always showing the two decimal places past
the decimal point. The line should contain no blanks.
Sample Input
1
5 4 6 7 8
2
4 2 7 8 9
7 3 4.5 6 7
-1
Sample Output
10.00
10.06
你要通过一个包含阻碍墙的房间来找到最短路径的长度。
在x=0,x=10,y=0,y=10时,总会有边。路径的初始和终点总是(0,5)和(10,5),也会有从0到18的垂直墙,每一个都有两道门。
输出应该包含每个房间的一行输出。这一行应该包含小数点后两位小数的最小路径长度,并且总是显示小数点后两位小数。这条线不应该有空格。 把所有点拿出来连边建图,判断一下中间是否有挡住的墙壁即可。
这里的线段判断相交用的方法很菜:判断两直线交点在不在线段上。
因为有除法误差可能比较大。 代码:
#include <stdio.h>
#include <string.h>
#include <algorithm>
#include <queue>
#include <math.h>
using namespace std;
typedef double f2;
#define N 10050
#define eps 1e-6
int head[N],to[N],nxt[N],cnt,n,vis[N],tot,S,T,ghj;
f2 val[N],dis[N];
priority_queue<pair<f2,int> >q;
//********************************************
struct Point {
f2 x,y;
Point() {}
Point(f2 x_,f2 y_) :
x(x_),y(y_) {}
Point operator + (const Point &p) const {return Point(x+p.x,y+p.y);}
Point operator - (const Point &p) const {return Point(x-p.x,y-p.y);}
Point operator * (f2 rate) const {return Point(x*rate,y*rate);}
};
f2 dot(const Point &p1,const Point &p2) {return p1.x*p2.x+p1.y*p2.y;}
f2 cross(const Point &p1,const Point &p2) {return p1.x*p2.y-p1.y*p2.x;}
Point a[N];
typedef Point Vector;
struct Line {
Point p;Vector v;
Line() {}
Line(const Point &p_,const Vector &v_) :
p(p_),v(v_) {}
};
Line b[N];
Point get_point(const Line &l1,const Line &l2) {
Vector u=l1.p-l2.p;
f2 t=cross(l2.v,u)/cross(l1.v,l2.v);
return l1.p+l1.v*t;
}
bool judge(const Point &p1,const Point &p2,const Line &l) {
if(l.p.x<p1.x+eps||l.p.x>p2.x-eps) return 0;
Line l1=Line(p1,p2-p1),l2=Line(l.p,l.v-l.p);
Point p3=get_point(l1,l2);
return p3.x>p1.x&&p3.x<p2.x&&p3.y>l.p.y&&p3.y<l.v.y;
}
//********************************************************
inline void add(int u,int v,f2 w) {
to[++cnt]=v; nxt[cnt]=head[u]; head[u]=cnt; val[cnt]=w;
}
void dij() {
memset(dis,0x7f,sizeof(dis));
memset(vis,0,sizeof(vis));
dis[S]=0;q.push(make_pair(0,S));
while(!q.empty()) {
int x=q.top().second;q.pop();
if(vis[x]) continue;
vis[x]=1;
int i;
for(i=head[x];i;i=nxt[i]) {
if(dis[to[i]]>dis[x]+val[i]) {
dis[to[i]]=dis[x]+val[i];
q.push(make_pair(-dis[to[i]],to[i]));
}
}
}
printf("%.2lf\n",dis[T]);
}
void init() {
memset(head,0,sizeof(head)); cnt=0; tot=0; ghj=0;
}
int main() {
while(scanf("%d",&n)&&n!=-1) {
int i,j,k;
init();
f2 x,y,z,w,h;
for(i=1;i<=n;i++) {
scanf("%lf%lf%lf%lf%lf",&x,&y,&z,&w,&h);
a[++tot]=Point(x,y);
b[++ghj]=Line(Point(x,0),a[tot]);
a[++tot]=Point(x,z);
a[++tot]=Point(x,w);
b[++ghj]=Line(a[tot-1],a[tot]);
a[++tot]=Point(x,h);
b[++ghj]=Line(a[tot],Point(x,10));
}
a[++tot]=Point(0,5); S=tot;
a[++tot]=Point(10,5); T=tot;
for(i=1;i<=tot;i++) {
for(j=1;j<=tot;j++) {
if(a[j].x>a[i].x+eps) {
int flg=1;
for(k=1;k<=ghj;k++) {
if(judge(a[i],a[j],b[k])) {
flg=0; break;
}
}
if(flg) {
add(i,j,sqrt((a[i].x-a[j].x)*(a[i].x-a[j].x)+(a[i].y-a[j].y)*(a[i].y-a[j].y)));
//printf("%.2lf\n",sqrt((a[i].x-a[j].x)*(a[i].x-a[j].x)+(a[i].y-a[j].y)*(a[i].y-a[j].y)));
}
}
}
}
dij();
}
}
POJ_1556_The Doors_判断线段相交+最短路的更多相关文章
- POJ 2556 (判断线段相交 + 最短路)
题目: 传送门 题意:在一个左小角坐标为(0, 0),右上角坐标为(10, 10)的房间里,有 n 堵墙,每堵墙都有两个门.每堵墙的输入方式为 x, y1, y2, y3, y4,x 是墙的横坐标,第 ...
- POJ 1556 计算几何 判断线段相交 最短路
题意: 在一个左下角坐标为(0,0),右上角坐标为(10,10)的矩形内,起点为(0,5),终点为(10,5),中间会有许多扇垂直于x轴的门,求从起点到终点在能走的情况下的最短距离. 分析: 既然是求 ...
- 简单几何(线段相交+最短路) POJ 1556 The Doors
题目传送门 题意:从(0, 5)走到(10, 5),中间有一些门,走的路是直线,问最短的距离 分析:关键是建图,可以保存所有的点,两点连通的条件是线段和中间的线段都不相交,建立有向图,然后用Dijks ...
- 还记得高中的向量吗?leetcode 335. Self Crossing(判断线段相交)
传统解法 题目来自 leetcode 335. Self Crossing. 题意非常简单,有一个点,一开始位于 (0, 0) 位置,然后有规律地往上,左,下,右方向移动一定的距离,判断是否会相交(s ...
- 【POJ 2653】Pick-up sticks 判断线段相交
一定要注意位运算的优先级!!!我被这个卡了好久 判断线段相交模板题. 叉积,点积,规范相交,非规范相交的简单模板 用了“链表”优化之后还是$O(n^2)$的暴力,可是为什么能过$10^5$的数据? # ...
- POJ 2653 Pick-up sticks(判断线段相交)
Pick-up sticks Time Limit: 3000MS Memory Limit: 65536K Total Submissions: 7699 Accepted: 2843 De ...
- 判断线段相交(hdu1558 Segment set 线段相交+并查集)
先说一下题目大意:给定一些线段,这些线段顺序编号,这时候如果两条线段相交,则把他们加入到一个集合中,问给定一个线段序号,求在此集合中有多少条线段. 这个题的难度在于怎么判断线段相交,判断玩相交之后就是 ...
- hdu 1086(判断线段相交)
传送门:You can Solve a Geometry Problem too 题意:给n条线段,判断相交的点数. 分析:判断线段相交模板题,快速排斥实验原理就是每条线段代表的向量和该线段的一个端点 ...
- POJ_1066_Treasure Hunt_判断线段相交
POJ_1066_Treasure Hunt_判断线段相交 Description Archeologists from the Antiquities and Curios Museum (ACM) ...
随机推荐
- Jhipster 学习(一)jhipster构建项目
如何安装jhipster 第一步:下载jdk 自己安装的1.8版本 (安装.环境变量配置略) 第二步:1.下载Eclipse (luna版 eclipse-4.4.1) 第三步:下载maven ( ...
- python---01.名片管理系统
这是第一篇文章,也是完整编写的第一份代码,,,,希望大神们多多指导,提出更好的想法. 第一部分-----提供选项的菜单栏 第二部分:根据用户输入的选择,提供功能 总体需要一个while True: 其 ...
- 使用jdk8 stream 统计单词数
在我的SpringBoot2.0不容错过的新特性 WebFlux响应式编程里面,有同学问如何使用stream统计单词数.这是个好例子,也很典型,在这里补上. 下面的例子实现了从一个文本文件读取(英文) ...
- Spring中对象和属性的注入方式
一:Spring的bean管理 1.xml方式 bean实例化三种xml方式实现 第一种 使用类的无参数构造创建,首先类中得有无参构造器(重点) 第二种 使用静态工厂创建 (1)创建静态的方法,返回类 ...
- 在Redis Sentinel环境下,jedis该如何配置
在Redis主从复制架构中,如果master出现了故障,则需要人工将slave提升为master,同时,通知应用侧更新master的地址.这样方式比较低效,对应用侧影响较大. 为了解决这个问题,Red ...
- Spring消息之WebSocket
一.WebSocket简介 WebSocket 的定义?WebSocket是HTML5下一种全双工通信协议.在建立连接后,WebSocket服务器端和客户端都能主动的向对方发送和接收数据,就像Sock ...
- java -- 对Map按键排序、按值排序
java -- 对Map按键.按值排序 1.按键排序(sort by key) 直接上代码 ↓ public Map<String, Str ...
- Day12 前端html
前端基础之HTML 老师博客: http://www.cnblogs.com/yuanchenqi/articles/6835654.html http://www.cnblogs.com/yuanc ...
- 使用FFmpeg捕获一帧摄像头图像
最近在研究FFmpeg,比较惊讶的是网上一大堆资料都是在说如何从已有的视频中截取一帧图像,却很少说到如何直接从摄像头中捕获一帧图像,其实我一直有个疑问,就是在Linux下,大家是用什么库来采集摄像头的 ...
- Java永久代去哪儿了
http://www.infoq.com/cn/articles/Java-PERMGEN-Removed 在Java虚拟机(以下简称JVM)中,类包含其对应的元数据,比如类的层级信息,方法数据和方法 ...