题目链接:http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3806
题目大意:给一个三角形的外接圆半径以及内切圆半径,求满足给出条件的三角形的三条边。
题目给出的样例有点坑.......容易误导人
Sample Input
1 2 2 5 9 9
Sample Ouput
3.464101615137754587 3.464101615137754587 3.464101615137754587 6 8 10 NO Solution!
给出的2和5的例子的时候其答案给出的是三个整数。所以会有点误导。
最开始看见题目的时候被样例误导了,一直没有什么思路,后来在纸上画了很久发现了一个特例。
YY给出的内切圆和外切圆的圆心是在一个直线上面的,然后是可以根据正弦定理以及一系列的变形得到长度x和角度α之间的关系。
然后数学公式可以得出:角度α和x的公式为
x =( 1 + 1 / sin(α) )/ (2 - 2*sin(α)*sin(α))
根据公式二分sin(α)
sin(α)的取值范围是0~1,比较与输入x 的大小,重新确定上界下界。(此函数是一个递增的)
求得sin(α)后可以根据x的大小以及α角度一些关系得到三角形的三条边。
注意变换之后默认的内切圆半径是1,故求得的三角形三边要乘于R/r
#include<iostream> #include<math.h> #include<cstring> #include<stdio.h> #include<algorithm> using namespace std; #define eps 1e-11 double er(double x) { double l = 0, r = 1, mid; while(l<r){ mid = (l+r)/2; //printf("%.9lf %.9lf\n",l,r); double temp = (1.0+1.0/mid)/(2.0-2.0*(mid*mid)); if(temp-x>eps) l = mid; else if(temp+eps<x) r = mid; else break; } //printf("%.13lf\n",mid); return mid; } int main () { double n,m; while(~scanf("%lf %lf",&n,&m)){ double bi=m/n; if((bi-2)<-eps) {printf("NO Solution!\n");continue;} double sinx=er(bi); double cosx=sqrt(1-sinx*sinx); double y = (1.0 + 1.0/sinx)/cosx; double t = (1.0+sinx)/cosx; printf("%.18lf %.18lf %.18lf\n",y*n,y*n,2*t*n); } }
忽略我的函数名称定义以及...... 出现的一个er(bi) ........
时间: 2024-11-05 14:42:38