【UVA10652】Board Wrapping(求凸包面积)
大致题意: 告诉你若干个矩形的重心坐标、长、宽和相对\(y\)轴的偏转角度,求矩形面积和与能围住这些矩形的最小凸包面积之比。
矩形面积和
这应该是比较好求的吧。
已经给了你长和宽,直接乘起来累加即可。
最小凸包面积
这道题关键还是在于求凸包面积。
首先,我们要注意将题目中给出的角度转换成弧度,还要记得取相反数,不然调死你。
这段代码可以与旋转函数放在一起:
inline Point Rotate(Vector A,double deg)
{
register double rad=deg*acos(-1)/180;dcmp(rad)<0&&(rad+=2*acos(-1)),rad=-rad;//将角度转换成弧度,并取相反数
return Vector(A.x*cos(rad)-A.y*sin(rad),A.x*sin(rad)+A.y*cos(rad));//返回旋转后的点的坐标
}
则我们就可以很方便地求出每个矩形四个顶点的坐标了。
枚举四个方向,分别将对应的向量(\(±\frac{s1}2\),\(±\frac{s2}2\))进行旋转,然后加上原先点的坐标即可(\(s1,s2\)分别为长和宽)。
这段代码如下:
A=Point(x,y),
P.p[++P.n]=A+Rotate(Point(s1/2,s2/2),deg),
P.p[++P.n]=A+Rotate(Point(s1/2,-s2/2),deg),
P.p[++P.n]=A+Rotate(Point(-s1/2,s2/2),deg),
P.p[++P.n]=A+Rotate(Point(-s1/2,-s2/2),deg);
这样,我们就可以得到\(4n\)个点,然后将这些点求一个凸包,然后作出凸包面积即可。
这段过程比较板子,可以参考这篇博客:初学计算几何(四)——初识凸包。
具体实现详见代码吧。
代码
#include<bits/stdc++.h>
#define N 600
using namespace std;
int n;
namespace ComputationGeometry
{
#define eps 1e-10
inline int dcmp(double x) {return fabs(x)<eps?0:(x>0?1:-1);}
struct Point
{
double x,y;
Point(double nx=0,double ny=0):x(nx),y(ny){}
};
typedef Point Vector;
inline Vector operator + (Point A,Point B) {return Vector(A.x+B.x,A.y+B.y);}
inline Vector operator - (Point A,Point B) {return Vector(A.x-B.x,A.y-B.y);}
inline Vector operator * (Vector A,double x) {return Vector(A.x*x,A.y*x);}
inline Vector operator / (Vector A,double x) {return Vector(A.x/x,A.y/x);}
inline bool operator < (Vector A,Vector B) {return fabs(A.x-B.x)>eps?A.x<B.x:A.y<B.y;}
inline double Cro(Vector A,Vector B) {return A.x*B.y-A.y*B.x;}
inline Point Rotate(Vector A,double deg)//旋转
{
register double rad=deg*acos(-1)/180;dcmp(rad)<0&&(rad+=2*acos(-1)),rad=-rad;
return Vector(A.x*cos(rad)-A.y*sin(rad),A.x*sin(rad)+A.y*cos(rad));
}
struct Polygon
{
int n;Point p[(N<<2)+5];
Polygon() {n=0;}
};
typedef Polygon ConvexHull;
inline double PolygonArea(Polygon P)//求多边形(凸包)面积
{
register int i;register double res=0;
for(i=2;i<P.n;++i) res+=Cro(P.p[i]-P.p[1],P.p[i+1]-P.p[1])/2;
return res;
}
inline ConvexHull GetConvexHull(Polygon P)//求凸包
{
register int i,t;register Polygon S=P;register ConvexHull res;
for(sort(S.p+1,S.p+S.n+1),i=1;i<=S.n;++i)
{
while(res.n>1&&dcmp(Cro(res.p[res.n]-res.p[res.n-1],S.p[i]-res.p[res.n-1]))<=0) --res.n;
res.p[++res.n]=S.p[i];
}
for(t=res.n,i=S.n-1;i;--i)
{
while(res.n>t&&dcmp(Cro(res.p[res.n]-res.p[res.n-1],S.p[i]-res.p[res.n-1]))<=0) --res.n;
res.p[++res.n]=S.p[i];
}
return res;
}
};
using namespace ComputationGeometry;
int main()
{
register int test_tot,i;register double x,y,s1,s2,deg,sum;register Point A;register Polygon P;register ConvexHull H;scanf("%d",&test_tot);
while(test_tot--)
{
for(scanf("%d",&n),P.n=sum=0,i=1;i<=n;++i)
{
scanf("%lf%lf%lf%lf%lf",&x,&y,&s1,&s2,°),A=Point(x,y),sum+=s1*s2,//同时统计矩形面积和
P.p[++P.n]=A+Rotate(Point(s1/2,s2/2),deg),P.p[++P.n]=A+Rotate(Point(s1/2,-s2/2),deg),P.p[++P.n]=A+Rotate(Point(-s1/2,s2/2),deg),P.p[++P.n]=A+Rotate(Point(-s1/2,-s2/2),deg);//存储点
}
printf("%.1lf %%\n",100*sum/PolygonArea(GetConvexHull(P)));//计算答案
}
return 0;
}
【UVA10652】Board Wrapping(求凸包面积)的更多相关文章
- poj 3348:Cows(计算几何,求凸包面积)
Cows Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 6199 Accepted: 2822 Description ...
- poj3348(求凸包面积)
题目链接:https://vjudge.net/problem/POJ-3348 题意:转换题意后即是求凸包的面积. 思路: 套模板,求凸包面积即转换为多个三角形面积之和,用叉积求,然后除2,因为本题 ...
- poj 3348 Cows 求凸包面积
题目链接 大意: 求凸包的面积. #include <iostream> #include <vector> #include <cstdio> #include ...
- uva109求凸包面积,判断点是不是在凸包内
自己想了一个方法判断点是不是在凸包内,先求出凸包面积,在求由点与凸包上每两个点之间的面积(点已经排好序了),如果两者相等,则点在凸包内,否则不在(时间复杂度可能有点高)但是这题能过 #include& ...
- UVA 10652 Board Wrapping(凸包)
题目链接:http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=32286 [思路] 凸包 根据角度与中心点求出长方形所有点来,然后就 ...
- UVA10652 Board Wrapping
题意 PDF 分析 就是一个裸的凸包. 如何确定点?就用中心向四边连垂直的向量然后旋转,加上中心点,即可得出旋转后的点. 时间复杂度\(O(T n \log n)\) 代码 #include<i ...
- POJ 3348 - Cows 凸包面积
求凸包面积.求结果后不用加绝对值,这是BBS()排序决定的. //Ps 熟练了template <class T>之后用起来真心方便= = //POJ 3348 //凸包面积 //1A 2 ...
- poj3348凸包面积
用叉积求凸包面积 如图所示,每次找p[0]来计算,(叉积是以两个向量构成的平行四边形的面积,所以要/2) #include<map> #include<set> #includ ...
- (模板)poj1113(graham扫描法求凸包)
题目链接:https://vjudge.net/problem/POJ-1113 题意:简化下题意即求凸包的周长+2×PI×r. 思路:用graham求凸包,模板是kuangbin的. AC code ...
随机推荐
- jzoj3208. 【JSOI2013】编程作业(kmp)
题面 Description Will相信,很多同学都有过这样的经历:大牛已经写好了编程作业,而作为菜鸟的自己不会写怎么办呢?拿大牛的代码抄一下嘛!但是提交一模一样的作业是不是不太好?于是就改一改变量 ...
- 1、gitlab的理论知识
2.1 svn与git对比 . svn git 分布式 不是 是 在线阅读 不支持 不仅支持,而且可以在线编辑 存储方式 按文件 按元数据 完整性 一般 优 离线工作 日志都没法看 完全没问题 分支 ...
- 使用命令安装vue插件
使用命令npm install element-ui --save-dev 安装element-ui. --save-dev表示自动添加配置依赖到package.json文件的devDependenc ...
- JS滑动下划线导航菜单实现原理
效果如下:http://campus.51job.com/test/zengxl/js html: <div class="mainnav"> <div clas ...
- Chinese Zodiac (水题)
The Chinese Zodiac, known as Sheng Xiao, is based on a twelve-year cycle, each year in the cycle rel ...
- ResourceBundle 读取properties文件中文乱码
1.确认properties文件是什么编码格式,并确认文件在该格式下中文是正常显示的2.读取时候,进行转一层,先用ISO-8859-1读取字节流,然后根据properties的文件格式进行new St ...
- Hadoop_配置Hadoop开发环境(Eclipse)
通常我们可以用Eclipse作为Hadoop程序的开发平台. 1) 下载Eclipse 下载地址:http://www.eclipse.org/downloads/ 根据操作系统类型,选择合适的版本 ...
- Ubuntu ls可以查看到文件,图形界面却看不到
解决方法:图形界面 Ctrl + h ,就可以显示出来隐藏文件
- about 字节
关于由于赋值导致字节的截断.字节扩展及数据类型的提升: 一.字节截断:int----->char 当一个字节(8位)放不下时,出现截断,直接取(最后一个字节)最后面面8位. 例如:1000000 ...
- Java多线程与并发——生产者与消费者应用案例
多线程的开发中有一个最经典的操作案例,就是生产者-消费者,生产者不断生产产品,消费者不断取走产品. package com.vince; /** * 生产者与消费者案例 * @author Admin ...