hdu 3263 Ancient vending machine
题目:给定一个多边形A,问能否穿过多边形的洞B。分析:计算几何、凸包、旋转卡壳、点与多边形关系。问题实际是在求多边形A的最小宽度和多边形B能容纳的最常线段长度。1.对于多边形A,构造凸包利用,旋转卡壳求出对踵点对,然后求出最小的高。2. 对于多边形B,所求的最长线段,一定经过多边形上的至少两个点,枚举所有点对,计算被截取的最长部分即可。[cpp]#include <algorithm>#include <iostream>#include <cstdlib>#include <cstdio>#include <cmath>using namespace std;typedef struct pnode{double x,y,d;pnode( double a, double b ) {x = a;y = b;}pnode(){};}point;point H[ 21 ];point C[ 21 ];point P0,Pn;typedef struct lnode{double x,y,dx,dy,d;int id,hit,sign;lnode( point a, point b ) {x = a.x;y = a.y;dx = b.x-a.x;dy = b.y-a.y;}lnode(){};}line;//两点间距离double dist( point a, point b ){return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));}//点到直线距离double dist( point a, line l ){return fabs(l.dx*(a.y-l.y)-l.dy*(a.x-l.x))/sqrt(l.dx*l.dx+l.dy*l.dy);}//叉乘 ab*acdouble crossproduct( point a, point b, point c ){return (b.x-a.x)*(c.y-a.y)-(c.x-a.x)*(b.y-a.y);}//坐标排序bool cmp1( point a, point b ){if ( a.x == b.x ) return a.y < b.y;else return a.x < b.x;}//级角排序bool cmp2( point a, point b ){double cp = crossproduct( P0, a, b );if ( cp == 0 ) return a.d < b.d;else return cp > 0;}//凸包扫描算法double Graham( int N ){sort( C+0, C+N, cmp1 );P0 = C[0];for ( int i = 1 ; i < N ; ++ i )C[i].d = dist( P0, C[i] );sort( C+1, C+N, cmp2 );//计算凸包int top = 2;for ( int i = 3 ; i < N ; ++ i ) {while ( top > 0 && crossproduct( C[top-1], C[top], C[i] ) <= 0 ) -- top;C[++ top] = C[i];}C[++ top] = C[0];//旋转卡壳,求对踵点对int L = 0,R = 1;double D = 500.000;do{while ( crossproduct( C[R], C[L], C[(L+1)%top] ) <= crossproduct( C[(R+1)%top], C[L], C[(L+1)%top] ) )R = (R+1)%top;D = min( D, dist( C[R], line( C[L], C[(L+1)%top] ) ) );L = (L+1)%top;}while ( L );return D;}//直线与线段相交判断bool l_cross_s( line b, line a ){double t1 = b.dx*(a.y-b.y)-b.dy*(a.x-b.x);double t2 = b.dx*(a.y+a.dy-b.y)-b.dy*(a.x+a.dx-b.x);return t1*t2 < 0;}//线段相交bool s_cross_s( line a, line b ){double t1 = 0.0+a.dx*(b.y-a.y)-a.dy*(b.x-a.x);double t2 = 0.0+a.dx*(b.y+b.dy-a.y)-a.dy*(b.x+b.dx-a.x);double t3 = 0.0+b.dx*(a.y-b.y)-b.dy*(a.x-b.x);double t4 = 0.0+b.dx*(a.y+a.dy-b.y)-b.dy*(a.x+a.dx-b.x);return (t1*t2 < 0)&&(t3*t4 < 0);}//点在线段上bool on( point p, line l ){if ( l.dx*(p.y-l.y)-l.dy*(p.x-l.x) == 0 )if ( (p.x-l.x)*(p.x-l.x-l.dx) <= 0 )if ( (p.y-l.y)*(p.y-l.y-l.dy) <= 0 )return true;return false;}//点在多边形内bool in( point p, point* P, int n ){double d[4][2] = {-101,-103,-103,101,101,-103,101,103};for ( int t = 0 ; t < 4 ; ++ t ) {line s1 = line( p, point( d[t][0], d[t][1] ) );int count = 0;for ( int i = 0 ; i < n ; ++ i ) {line s2 = line( P[i], P[i+1] );if ( on( p, s2 ) ) return true;if ( s_cross_s( s1, s2 ) ) count ++;if ( on( P[i], s1 ) && l_cross_s( s1, line( P[i+1], P[(i-1+n)%n] ) ) ) count ++;}if ( count%2 == 0 ) return false;}return true;}&补充:软件开发 , C++ ,
上一个:HAC-UM无线数传模块使用总结
下一个:数位和乘积(高精组合数学)
- 更多C/C++疑问解答:
- 关于c++的cout输出的问题。
- 在学校里学过C和C++,不过学的很一般,现在自学C#,会不会很难?
- 全国计算机二级C语言笔试题
- 已知某树有2个2度结点,3个3度结点,4个4度结点,问有几个叶子结点?
- c++数据结构内部排序问题,整数排序
- 2012九月计算机二级C语言全国题库,,急求急求
- 如果assert只有一个字符串作为参数,是什么意思呢?
- C语言中,哪些运算符具有左结合性,哪些具有右结合性,帮忙总结下,谢谢了!
- 为什么用结构体编写的程序输入是,0输不出来啊~~~
- 将IEEE—754的十六进制转化为十进制浮点类型,用C或C++都行,多谢各位大侠啊,非常感谢!
- 为什么这个程序求不出公式?
- 这个链表倒置的算法请大家分析下
- c语言函数库调用
- C语言unsigned int纠错
- C语言快排求解啊