http://codeforces.com/contest/935/problem/C
半径R, 中心(x1,y1)の円Cと(円の外かもしれない)頂点P(x2,y2)がある。
これについて以下の条件を満たす円C'の半径と中心を答えよ。
- 円C'は円Cの内部にある
- 円C'は頂点Pを含まない
- 円C'は上の2条件を満たす中で半径が最大
解法
http://codeforces.com/contest/935/submission/35487154
「d := 円Cの中心と点Pとの距離」とする。
まず、コーナーケースを説明しておこう。
1つ目は頂点Pが円Cの中心である場合である(d == 0だがソース中ではd<1e-9のこと。1e-9はeps)
この場合では半径はR/2の円が最大で書ける。
中心は適当な所に取ればいいが、(X1+ R/2, Y1)がお手軽。
2つ目は頂点Pが円Cの外にある場合である(R≦d)
この場合では円C'は円Cと全く同じになる。
それ以外の場合では円Cに内接し、頂点Pと接するように円C'を書いてやると、半径は(R+d)/2となる。
中心は(X2 + (X1-X2)*R/d, Y2+(Y1-Y2)*R/d)となる。
これはベクトルを使って求めているが、元々は「(X2,Y2) + (X1-X2,Y1-Y2) * R / d」
double R, X1, Y1, X2, Y2; //--------------------------------------------------------------------------------------------------- void _main() { cin >> R >> X1 >> Y1 >> X2 >> Y2; double d = sqrt((X1 - X2)*(X1 - X2) + (Y1 - Y2)*(Y1 - Y2)); if(d < 1e-9) printf("%.10f %.10f %.10f\n", X1 + R / 2, Y1, R / 2); else if (R <= d) printf("%.10f %.10f %.10f\n", X1, Y1, R); else { double r = (R + d) / 2; double x = X2 + (X1 - X2) * r / d; double y = Y2 + (Y1 - Y2) * r / d; printf("%.10f %.10f %.10f\n", x, y, r); }