http://acm.hdu.edu.cn/showproblem.php?pid=4998

这道题,在比赛的时候看了很久,才明白题目的大意。都怪自己不好好学习英语。后来经过队友翻译才懂是什么意思。

题目大意:二维平面内的物品,把它们绕给定的n个点,逆时针旋转。 现在求通过一个A点,逆时针旋转角度P就能完成这个操作。

问:这个点A的坐标,P的角度。

解题思路:随意找个点t1,绕着n个点旋转得到t2。点A一定在线段t1t2的垂直平分线上。再找一点t3,绕n个点旋转得到t4。

线段t1t2的垂直平分线和线段t3t4的垂直平分线相交一点,这点就是A点。证明过程就不写了,可以画图看看。

旋转的角度是向量At1和向量At2的夹角Θ,或是2∏-Θ

 #include<cstdio>
#include<cmath>
#include<iostream>
using namespace std; struct Point{
double x, y; Point(double x = , double y = ): x(x), y(y){}
}; typedef Point Vector; const double eps = 1e-; int dcmp(double x){
if(fabs(x) < eps)
return ;
return x < ? - : ;
} bool operator == (Point A, Point B){
return dcmp(A.x - B.x) == && dcmp(A.y - B.y) == ;
} Vector operator + (Vector A, Vector B){
return Vector(A.x + B.x, A.y + B.y);
} Vector operator - (Vector A, Vector B){
return Vector(A.x - B.x, A.y - B.y);
} Vector operator * (Vector A, double p){
return Vector(A.x * p, A.y * p);
} Vector operator / (Vector A, double p){
return Vector(A.x / p, A.y / p);
} double dot(Vector A, Vector B){//点乘
return A.x * B.x + A.y * B.y;
} double length(Vector A){//向量的模
return sqrt(dot(A, A));
} double angle(Vector A, Vector B){//两个向量的夹角
return acos(dot(A, B) / length(A) / length(B));
} Vector rotate(Vector A, double rad){//点A绕原点旋转角度为rad
return Vector(A.x * cos(rad) - A.y * sin(rad), A.x * sin(rad) + A.y * cos(rad));
} Vector normal(Vector A){//向量的法向量
double L = length(A);
return Vector(-A.y / L, A.x / L);
} double cross(Vector A, Vector B){//叉乘
return A.x * B.y - A.y * B.x;
} int n;
Point p[];
double ra[]; void input(){
cin>> n;
for(int i = ; i < n; ++i){
cin>> p[i].x>> p[i].y>> ra[i];
if(dcmp(ra[i] - * acos(-1.0)) == || dcmp(ra[i]) == ){
//当输入的弧度为0或者2π时,都是没用的
ra[i] = ;
n--;
i--;
}
}
} Vector rotate_point(Vector A){//将A点绕n个点旋转
for(int i = ; i < n; ++i){
A = p[i] + rotate(A - p[i], ra[i]);
}
return A;
} Vector mid_point(Point A, Point B){//求两点之间的中点
return Vector((A.x + B.x) / , (A.y + B.y) / );
} Point get_line_intersection(Point P, Vector v, Point Q, Vector w){//两直线求交点,《算法入门经典训练之南》几何
Vector u = P - Q;
double t = cross(w, u) / cross(v, w);
return P + v * t;
} void solve(){
Point t1[], t2[], mid[], vec[];
t1[].x = -;
t1[].y = -;
t1[].x = -;
t1[].y = -;
for(int i = ; i < ; ++i){
t2[i] = rotate_point(t1[i]);
mid[i] = mid_point(t1[i], t2[i]);
vec[i] = normal(t1[i] - t2[i]);
}
Point ans = get_line_intersection(mid[], vec[], mid[], vec[]);//答案点A
double ansp = angle(t1[] - ans, t2[] - ans);//旋转角度P if(cross(t1[] - ans, t2[] - ans) < ){//判断是ansp 还是2π - ansp
ansp = * acos(-1.0) - ansp;
} if(dcmp(ans.x) == ){//加入答案是-1e-11,如果直接输出就会是-0.0000000000
ans.x = ;
}
if(dcmp(ans.y) == ){
ans.y = ;
} printf("%.10lf %.10lf %.10lf\n", ans.x, ans.y, ansp);
} int main(){
//freopen("data.in", "r", stdin);
//freopen("data.out", "w", stdout);
int t;
cin>> t;
while(t--){
input();
solve();
}
return ;
}

AC代码

hdu 4998的更多相关文章

  1. HDU 4998 Rotate (计算几何)

    HDU 4998 Rotate (计算几何) 题目链接http://acm.hdu.edu.cn/showproblem.php?pid=4998 Description Noting is more ...

  2. hdu 4998 矩阵表示旋转

    http://acm.hdu.edu.cn/showproblem.php?pid=4998 http://blog.csdn.net/wcyoot/article/details/33310329 ...

  3. HDU 4998 Rotate --几何

    题意:给n个点(x,y,p),从1~n,一次每次所有点绕着第 i 个点(原来的)逆时针转pi个弧度,问最后所有点的位置相当于绕哪个点旋转多少弧度,求出那点X和弧度P 解法:直接模拟旋转,每次计算新的坐 ...

  4. HDU 4998 (点的旋转) Rotate

    为了寻找等效旋转操作,我们任选两个点P0和Q0,分别绕这n个点旋转一定的角度后最终得到Pn和Qn 然后已知:P0和Pn共圆,Q0和Qn共圆.所以要找的等效旋转点就是这两个线段的垂直平分线交点O. 等效 ...

  5. HDU 4998 Rotate

    题意: n次旋转  每次平面绕ai点旋转pi弧度  问  最后状态相当于初始状态绕A点旋转P弧度  A和P是多少 思路: 如果初始X点的最后状态为X'点  则圆心一定在X和X'连线的垂直平分线上  那 ...

  6. hdu 4998 Rotate 点的旋转 银牌题

    Rotate Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Subm ...

  7. HDOJ 2111. Saving HDU 贪心 结构体排序

    Saving HDU Time Limit: 3000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total ...

  8. 【HDU 3037】Saving Beans Lucas定理模板

    http://acm.hdu.edu.cn/showproblem.php?pid=3037 Lucas定理模板. 现在才写,noip滚粗前兆QAQ #include<cstdio> #i ...

  9. hdu 4859 海岸线 Bestcoder Round 1

    http://acm.hdu.edu.cn/showproblem.php?pid=4859 题目大意: 在一个矩形周围都是海,这个矩形中有陆地,深海和浅海.浅海是可以填成陆地的. 求最多有多少条方格 ...

随机推荐

  1. Linux的权限说明

    Linux的权限不是很细致,只有RWX三种r(Read,读取):对文件而言,具有读取文件内容的权限:对目录来说,具有浏览目录的权限.w(Write,写入):对文件而言,具有新增,修改,删除文件内容的权 ...

  2. [转]C#之反射

    前言 之所以要写这篇关于C#反射的随笔,起因有两个:   第一个是自己开发的网站需要用到   其次就是没看到这方面比较好的文章. 所以下定决心自己写一篇,废话不多说开始进入正题. 前期准备 在VS20 ...

  3. Google物联网操作系统协同框架Weave深度解析

    1.       Google Weave框架 在2015年的Google I/O大会上,负责Android业务的桑达.皮查伊(SundarPichai)宣布了Google最新的物联网战略.这包括一个 ...

  4. C# 中==与Equals方法比较

    先来段代码,如下: static void Main(string[] args) { string a = new string(new char[] { 'h', 'e', 'l', 'l', ' ...

  5. 20145211《Java程序设计》第5周学习总结——独上高楼,望尽天涯路

    教材学习内容总结 异常处理 JAVA异常 异常指不期而至的各种状况,如:文件找不到.网络连接失败.非法参数等.异常是一个事件,它发生在程序运行期间,干扰了正常的指令流程.异常就是出现在运行时出现不正常 ...

  6. Java冒泡排序,Java对象冒泡排序

    今天呆公司特别无聊,百度了一下Java机试题,看到一个冒泡排序. 粘上我全部的代码: 实体类: package accp.com.internet;/** * 人物类 * @author xuxiao ...

  7. C# Socket编程 同步以及异步通信

    套接字简介:套接字最早是Unix的,window是借鉴过来的.TCP/IP协议族提供三种套接字:流式.数据报式.原始套接字.其中原始套接字允许对底层协议直接访问,一般用于检验新协议或者新设备问题,很少 ...

  8. iOS Block传值

    上个月,针对block恶补了一下,以为自己全部掌握了,其实不尽然. 昨天项目中在下载的时候用到,自己竟然不知道该从何下手,惭愧~ 情景是这个样子的:我写了个下载类,阴老师在调用时,将参数(sid,UR ...

  9. mac开启服务命令

    开启mysql   mysql.server start 开启nginx         sudo  nginx 重启nginx   sudo  nginx   -s   reload 开启apach ...

  10. imx6 system boot

    imx6开机启动就进入download模式,有的板子进入文件系统之后会进入download模式.查看datasheet,Chapter 8 System Boot查找原因,记录于此. freescal ...