hdu 4404 Worms
来源:互联网 发布:极简装修 知乎 编辑:程序博客网 时间:2024/04/30 10:36
http://hi.baidu.com/billdu/item/703ad4e15d819db52f140b0b 根据这个思路写的。
将圆与三角形的交按照0、1、2个交点分类
然后就好做多啦,有效面积是个强大的工具
买一送2,poj 3675,2986一样可以用模板过掉。
咔咔。有自己的模板真好~~
#include <set>#include <map>#include <queue>#include <stack>#include <math.h>#include <stdio.h>#include <stdlib.h>#include <iostream>#include <limits.h>#include <string.h>#include <string>#include <algorithm>#define MID(x,y) ( ( x + y ) >> 1 )#define L(x) ( x << 1 )#define R(x) ( x << 1 | 1 )#define FOR(i,s,t) for(int i=(s); i<(t); i++)#define FORD(i,s,t) for(int i=(s-1); i>=t; i--)#define BUG puts("here!!!")#define STOP system("pause")#define file_r(x) freopen(x, "r", stdin)#define file_w(x) freopen(x, "w", stdout)using namespace std;const int MAX = 110;const double pi = acos(-1.0);struct point {double x, y;};point p[MAX];point c;double r;const double eps = 1e-8;int dcmp(double x) {return x < -eps ? -1 : x > eps ? 1 : 0;}double disp2p(point a,point b) // a b 两点之间的距离 {return sqrt( ( a.x - b.x ) * ( a.x - b.x ) + ( a.y - b.y ) * ( a.y - b.y ) );}double crossProduct(point a,point b,point c)//向量 ac 在 ab 的方向 顺时针是正 {return (c.x - a.x)*(b.y - a.y) - (b.x - a.x)*(c.y - a.y);}point l2l_inst_p(point u1,point u2,point v1,point v2){point ans = u1;double t = ((u1.x - v1.x)*(v1.y - v2.y) - (u1.y - v1.y)*(v1.x - v2.x))/((u1.x - u2.x)*(v1.y - v2.y) - (u1.y - u2.y)*(v1.x - v2.x));ans.x += (u2.x - u1.x)*t;ans.y += (u2.y - u1.y)*t;return ans;}//直线与圆的交点 int l2c_inst_p(point c,double r,point l1,point l2,point *pv){int cnt = 0;double d = fabs( crossProduct(c,l1,l2) )/disp2p(l1,l2);if( dcmp(d-r) > 0 )return 0;point p = c;double t;p.x += l1.y - l2.y;p.y += l2.x - l1.x;p = l2l_inst_p(p,c,l1,l2);t = sqrt(r*r - disp2p(p,c)*disp2p(p,c))/disp2p(l1,l2);pv[cnt].x = p.x + (l2.x - l1.x)*t;pv[cnt++].y = p.y + (l2.y - l1.y)*t;if( dcmp(d-r) == 0 )return cnt;pv[cnt].x = p.x - (l2.x - l1.x)*t;pv[cnt++].y = p.y - (l2.y - l1.y)*t;return cnt;}//若不包括端点,将等于号去掉 bool onSegment(point a, point b, point c){//和端点重合 if( dcmp(c.x - a.x) == 0 && dcmp(c.y - a.y) == 0 || dcmp(c.x - b.x) == 0 && dcmp(c.y - b.y) == 0 )return false; if( dcmp(crossProduct(a,b,c)) == 0 && dcmp(c.x - min(a.x,b.x)) >= 0 && dcmp(c.x-max(a.x,b.x)) <= 0 && dcmp(c.y - min(a.y,b.y)) >= 0 && dcmp(c.y-max(a.y,b.y)) <= 0 )return true;return false;}//求线段与圆的交点,p中存放交点,返回交点个数 //若不包括端点,需要在onSegment函数中控制一下 int seg2c_inst_p(point c,double r,point l1,point l2,point *p){point pv[3];int cnt = l2c_inst_p(c, r, l1, l2, pv);int cntp = 0;FOR(i, 0, cnt)if( onSegment(l1, l2, pv[i]) )p[cntp++] = pv[i];//按照交点离l1的顺序从小到大排序 if(cntp == 2 ) {if(disp2p(p[0], l1) > disp2p(p[1], l1) )swap(p[0], p[1]);}return cntp;}double area_triangle(point a,point b,point c){return fabs( crossProduct(a,b,c) )/2.0;}//求以acb为圆心角的扇形(小于180度) double area_shan(point a, point b, point c, double r) {double aa = disp2p(c, b);double bb = disp2p(a, c);double cc = disp2p(a, b);double ang = acos((aa*aa + bb*bb - cc*cc)/(2*aa*bb));return ang/2*r*r;}//三角形与圆的交面积,其中c是圆心 double area_triangle2circle(point a, point b, point c, double r) {point p[3];int cnt = seg2c_inst_p(c, r, a, b, p);if( dcmp(crossProduct(a, b, c)) == 0 ) return 0;if( cnt == 0 ) {if( dcmp(disp2p(a, c) - r) <= 0 && dcmp(disp2p(b, c) - r) <= 0 )return area_triangle(a, b, c);elsereturn area_shan(a, b, c, r); }if( cnt == 1 ) {if( dcmp(disp2p(a, c) - r) > 0 && dcmp(disp2p(b, c) - r) > 0 )return area_shan(a, b, c, r);if( dcmp(disp2p(a, c) - r) > 0 ) swap(a, b);return area_shan(p[0], b, c, r) + area_triangle(a, p[0], c);}if( cnt == 2 ) {return area_shan(a, p[0], c, r) + area_shan(p[1], b, c, r)+ area_triangle(p[0], p[1], c);}}double solve(int n) {double area = 0;FOR(i, 0, n) {area += area_triangle2circle(p[i], p[(i+1)%n], c, r) * dcmp(crossProduct(c, p[(i+1)%n], p[i]));}return fabs(area);}void cal(double x0,double y0,double v0,double a,double t,double g){ double yt = v0*sin(a); double xt = v0*cos(a); double xx = x0 + xt*t; double yy = y0 + yt*t-0.5*g*t*t; c.x = xx; c.y = yy;}int main() {int n;double x, y, v, ang, t, g;while( ~scanf("%lf%lf%lf%lf%lf%lf%lf", &x, &y, &v, &ang, &t, &g, &r) ) {if( x == y && y == v && v == ang && ang == t && t == g && g == r && r == 0 )break;scanf("%d", &n);FOR(i, 0, n)scanf("%lf%lf", &p[i].x, &p[i].y);cal(x, y, v, ang/180*pi, t, g);double ans = solve(n);printf("%.2lf\n", ans);}return 0;}
- hdu 4404 Worms
- hdu 4404 worms #by nobody
- hdu 4404 Worms (2012金华网络赛E题)
- hdu 4404 Worms(多边形与圆的交)
- Worms
- HDU 4404 Worms(任意多边形与圆相交部分的面积)
- HDU4404 Worms
- B. Worms
- B. Worms
- hdoj.4404 Worms【计算几何+圆与多边形相交面积】 2015/08/17
- Google Search API Worms
- <cf>Worms Evolution
- Worms(水题)
- [Codeforces] 474B - Worms
- CodeForces 474B(Worms)
- 【CODEFORCES】 B. Worms
- CF 474B Worms
- A. Worms Evolution
- 创建使用dll
- 实验五 单表查询(V2.0版)
- HDU 1423 最大公共递增子序列长度
- dojo(二):事件处理
- 程序员的谎谬之言还是至理名言?
- hdu 4404 Worms
- Java基础——动态绑定
- Scala Trait 的线性化
- C用语言中的数组与指针
- 送给程序员:最好的编程名言
- WINCE6 添加唯一的设备ID 用户不可修改
- 黑马程序员_IO流_3
- Linux vi学习笔记
- C/C++学习笔记(十)标准模板库STL和string