The Doors

Time Limit: 1000MS Memory Limit: 10000K

Description

You are to find the length of the shortest path through a chamber containing obstructing walls. The chamber will always have sides at x = 0, x = 10, y = 0, and y = 10. The initial and final points of the path are always (0, 5) and (10, 5). There will also be from 0 to 18 vertical walls inside the chamber, each with two doorways. The figure below illustrates such a chamber and also shows the path of minimal length.



Input

The input data for the illustrated chamber would appear as follows.

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

The 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

Source

Mid-Central USA 1996

一道相对来说偏综合的简单题,我们将墙拆成两个点,然后这道题的样例图示给了我们很好的思路:样例图示中整张图被巧妙地搞成了一张类分层图,而题目又让我们求从s" role="presentation" style="position: relative;">ss到t" role="presentation" style="position: relative;">tt的最短路径,题目中还巧妙地回避了有负边权的情况。既然这样,我们怎么可能不用dijstra" role="presentation" style="position: relative;">dijstradijstra来跑最短路呢?然后就是建图的问题了,最开始我想到的是相邻两层之间建边,但仔细一想这样会gg" role="presentation" style="position: relative;">gggg,于是改进一下建边的方法,对于每一个点,我们将它跟在它后面出现的点连边,边权的处理也很简单。如果两点之间可以直接抵达没有墙的间隔,那么直接将边权赋值为两点间的距离即可,如果有墙的间隔,我们不建边或者将边权赋成极大值,建完图之后跑最短路计算就行了。

然后还有一个坑点就是POJ" role="presentation" style="position: relative;">POJPOJ上用g++" role="presentation" style="position: relative;">g++g++的话double" role="presentation" style="position: relative;">doubledouble的输出只能用" role="presentation" style="position: relative;">(本蒟蒻因为这一点挂了10+" role="presentation" style="position: relative;">10+10+次)

代码如下:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<queue>
#include<cstring>
#include<cmath>
#define N 100005
#define eps 1e-15
using namespace std;
struct pot{double x,y;}p[N];
struct edge{int v,next;double w;}e[N];
struct line{pot a,b;}l[N];
struct heap{int u;double w;};
inline bool operator<(heap a,heap b){return a.w>b.w;}
int n,first[N],cnt=0,s,t,tot=0,totx=0;
double d[N];
bool vis[N];
inline void add(int u,int v,double w){
    e[++cnt].v=v;
    e[cnt].next=first[u];
    e[cnt].w=w;
    first[u]=cnt;
}
inline double dijsktra(){
    priority_queue<heap>q;
    for(int i=0;i<=tot;++i)d[i]=10000000000.0,vis[i]=false;
    d[s]=0.0;
    q.push((heap){s,d[s]});
    while(!q.empty()){
        heap x=q.top();
        q.pop();
        if(vis[x.u])continue;
        vis[x.u]=true;
        for(int i=first[x.u];i!=-1;i=e[i].next){
            int v=e[i].v;
            if(d[v]>d[x.u]+e[i].w){
                d[v]=d[x.u]+e[i].w;
                q.push((heap){v,d[v]});
            }
        }
    }
    return d[t];
}
inline double dis(pot a,pot b){return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));}
inline pot operator-(pot a,pot b){return (pot){a.x-b.x,a.y-b.y};}
inline double cross(pot a,pot b){return a.x*b.y-a.y*b.x;}
inline int sign(double x){return (x>eps)-(x<-eps);}
inline bool pd(pot a,pot b,pot c,pot d){return sign(cross(a-c,b-c))*sign(cross(a-d,b-d))<0;}
inline bool check(int a,int b){
    for(int i=1;i<=totx;++i)if(pd(p[a],p[b],l[i].a,l[i].b)&&pd(l[i].a,l[i].b,p[a],p[b]))return false;
    return true;
}
int main(){
    p[s=0].x=0.0,p[s].y=5.0;
    while(scanf("%d",&n)&&n!=-1){
        memset(first,-1,sizeof(first));
        cnt=0,tot=0,totx=0;
        for(int i=1;i<=n;++i){
            double x0,y1,y2,y3,y4;
            scanf("%lf%lf%lf%lf%lf",&x0,&y1,&y2,&y3,&y4);
            p[++tot].x=x0,p[tot].y=0.0;
            p[++tot].x=x0,p[tot].y=y1;
            p[++tot].x=x0,p[tot].y=y2;
            p[++tot].x=x0,p[tot].y=y3;
            p[++tot].x=x0,p[tot].y=y4;
            p[++tot].x=x0,p[tot].y=10.0;
            l[++totx].a=(pot){x0,0.0},l[totx].b=(pot){x0,y1};
            l[++totx].a=(pot){x0,y2},l[totx].b=(pot){x0,y3};
            l[++totx].a=(pot){x0,y4},l[totx].b=(pot){x0,10.0};
        }
        p[t=++tot].x=10.0,p[t].y=5.0;
        for(int i=s;i<=t;++i)
            for(int j=i+1;j<=t;++j)
                if(check(i,j))add(i,j,dis(p[i],p[j]));
                else add(i,j,10000000000.0);
        printf("%.2lf\n",dijsktra());
    }
    return 0;
}

2018.07.06 POJ1556 The Doors(最短路)的更多相关文章

  1. 2018.07.06 POJ1698 Alice's Chance(最大流)

    Alice's Chance Time Limit: 1000MS Memory Limit: 10000K Description Alice, a charming girl, have been ...

  2. EZ 2018 07 06 NOIP模拟赛

    又是慈溪那边给的题目,这次终于没有像上次那样尴尬了, T1拿到了较高的暴力分,T2没写炸,然后T3写了一个优雅的暴力就203pts,Rank3了. 听说其它学校的分数普遍100+,那我们学校还不是强到 ...

  3. 2018.07.06 BZOJ 1588: HNOI2002营业额统计(非旋treap)

    1588: [HNOI2002]营业额统计 Time Limit: 5 Sec Memory Limit: 162 MB Description 营业额统计 Tiger最近被公司升任为营业部经理,他上 ...

  4. 2018.07.06 BZOJ1208: HNOI2004宠物收养所(非旋treap)

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

  5. 2018.07.06 洛谷P2936 [USACO09JAN]全流Total Flow(最大流)

    P2936 [USACO09JAN]全流Total Flow 题目描述 Farmer John always wants his cows to have enough water and thus ...

  6. 2018.07.06 POJ 1459 Power Network(多源多汇最大流)

    Power Network Time Limit: 2000MS Memory Limit: 32768K Description A power network consists of nodes ...

  7. 2018.07.06 POJ2536 Gopher II(二分图匹配)

    Gopher II Time Limit: 2000MS Memory Limit: 65536K Description The gopher family, having averted the ...

  8. 2018.07.06 POJ1273 Drainage Ditches(最大流)

    Drainage Ditches Time Limit: 1000MS Memory Limit: 10000K Description Every time it rains on Farmer J ...

  9. 新手C#构造函数、继承、组合的学习2018.08.06/07

    构造函数,是一种特殊的方法.主要用来在创建对象时初始化对象,即为对象成员变量赋初始值,总与new运算符一起使用在创建对象的语句中.特别的一个类可以有多个构造函数,可根据其参数个数的不同或参数类型的不同 ...

随机推荐

  1. oracle 数据字典

    select * from dictionary; --数据字典 数据字典是Oracle存放有关数据库信息的地方,其用途是用来描述数据的. 比如一个表的创建者信息,创建时间信息,所属表空间信息,用户访 ...

  2. WinRAR命令行版本 rar.exe使用详解

    RAR 命令行语法~~~~~~~~~~~~~~ 语法 RAR.exe <命令>  [ -<开关> ]  <压缩文件>  [ <@列表文件...> ]   ...

  3. python, Django 的安装

    yum install zlib yum install zlib-devel yum install openssl-devel 否则导致安装setuptools出错,还需要重新编译python 如 ...

  4. memcache命令

    Command Description Example get 读取键值 get mykey set 设置新键值 set mykey 0 60 5 add 新增键值 add newkey 0 60 5 ...

  5. springboot+jsp 遇到的坑

    springboot  使用jsp: 1,修改配置文件, spring: mvc: view: prefix: /WEB-INF/jsp/ suffix: .jsp 2,pom 加入: <dep ...

  6. delphi 中判断对象是否具备某一属性

    Uses   TypInfo;         {$R   *.dfm}         procedure   TForm1.Button1Click(Sender:   TObject);     ...

  7. 遇到的IE不兼容问题总结

    IE浏览器兼容问题困扰多时,由于IE6不在进行修补,IE6的考虑也越来越少,有些IE遇到的不兼容的现象想做一个总结 1宽度或高度:IE的是width+border+margin+padding goo ...

  8. keras、 tensor flow 教程

    [keras]http://keras-cn.readthedocs.io/en/latest/getting_started/concepts/,[tensorflow] http://blog.c ...

  9. groovy 环境配置

    win7: 下载 http://www.groovy-lang.org/download.html 将解压后的文件夹里的bin目录加入path环境变量

  10. docker-composer

    1.安装docker-composer   参考官方 安装1.20.1 sudo curl -L https://github.com/docker/compose/releases/download ...