zoukankan      html  css  js  c++  java
  • poj 1066 Treasure Hunt 线段相交判断

         宝藏在一个矩形的内部,矩形内有纵横交错的墙形成多个房间,求最少炸掉多少道墙可到达宝藏所在的房间,宝藏不会在墙上,炸点必须在墙的中间点上,不会超过两个的墙相交以一点。
        若起点和宝藏点连线的线段和某直线相交,那么无论你怎么绕你都要穿过这条直线才能到达宝藏点。所以我们可以这样做:枚举矩形边上的所有点做为起点,(不需要求中点做为起点)。连接起点、宝藏点,求出这条线段会和多少条其它的直线相交。然后加1(因为也要炸掉矩形边),即为所求答案。
     
    #include<stdio.h>
    #include<stdlib.h>
    #include<iostream>
    #include<algorithm>
    using namespace std;
    struct point
    {
    double x,y;
    }p[100];
    double multi(point p0,point p1,point p2)
    {
    return (p1.x-p0.x)*(p2.y-p0.y)-(p2.x-p0.x)*(p1.y-p0.y);
    }
    bool is(point s1,point e1,point s2,point e2) //判断线段相交
    {
    return (max(s1.x,e1.x)>=min(s2.x,e2.x))&&
    (max(s2.x,e2.x)>=min(s1.x,e1.x))&&
    (max(s1.y,e1.y)>=min(s2.y,e2.y))&&
    (max(s2.y,e2.y)>=min(s1.y,e1.y))&&
    (multi(s1,s2,e1)*multi(s1,e1,e2)>0)&&
    (multi(s2,s1,e2)*multi(s2,e2,e1)>0);
    }
    int main()
    {
    int i,j,n,min,num;
    while(scanf("%d",&n)!=EOF)
    {
    n*=2;
    for(i=0;i<n+1;i++)
    scanf("%lf%lf",&p[i].x,&p[i].y);
    min=0x7fffffff;
    for(i=0;i<n;i++)
    {
    num=0;
    for(j=0;j<n;j+=2)
    {
    if(i==j||i==j+1)  //起点要不在这条线段上
    continue;
    if(is(p[i],p[n],p[j],p[j+1]))
    num++;
    }
    if(num<min)
    min=num;
    }
    if(n==0) //要注意墙数为零的情况
    min=0;
    printf("Number of doors = %d\n",min+1);
    }
    return 0;
    }
            
     
     
     
     
  • 相关阅读:
    where field in
    看看 高考
    高分的标准
    UCOS-消息邮箱(学习笔记)
    UCOS-互斥信号量(学习笔记)
    UCOS-信号量(学习笔记)
    RVMDK的DEBUG调试-实时数据查看
    OSTimeDelay(1)
    STM32中断控制及优先级设置
    MODBUS-RTU学习
  • 原文地址:https://www.cnblogs.com/zxj015/p/2740223.html
Copyright © 2011-2022 走看看