您的位置:首页 > 其它

[codevs3273]两圆的交 计算几何

2015-10-13 07:09 169 查看
用了math库函数,反正code没限制,懒得自己写了

Uses Math;
var a,b,c,d,e,f,h,m,n,g,o,p:double;
begin
read(a,b,c,d,e,f);
if c<f then begin g:=c;c:=f;f:=g;end;
h:=hypot(a-d,b-e);
if h>=c+f then begin write('0.000');halt;end;
if c>=f+h then begin write(pi*f*f:0:3);halt;end;
m:=(c*c-f*f+h*h)/2/h;
n:=sqrt(c*c-m*m);
o:=c*c*pi*(arcsin(n/c)/pi)-n*m;
p:=f*f*pi*(arcsin(n/f)/pi)-n*abs(h-m);
if m>h then p:=f*f*pi-p;
write(o+p:0:3);
end.


View Code
简单解释一下吧,math库自带pi函数,貌似是多少位都可以(没试过,反正前20位没压力),其次,hypot函数中给出两个double变量a和b,返回另一个double变量c,表示以a,b为直角边的直角三角形斜边长为c。有了这两个函数,这道题就很简单了

我们对输入数据做一下处理,使大圆在前。可以不用交换坐标。{if c<f then begin g:=c;c:=f;f:=g;end;}

然后就要计算两个圆的焦点了。我们先算出两圆的圆心距离h,可以判断特殊情况。{h:=hypot(a-d,b-e);}

有两种特殊情况是没有交点的,就是相离和包含(把相切也算在里面)。我们要排除这两种特殊情况。

相离时两圆半径和c+f≤圆心距离h。{if h>=c+f then begin write('0.000');halt;end;}

包含时小圆半径f+圆心距离h≤大圆半径c。{if c>=f+h then begin write(pi*f*f:0:3);halt;end;}

特殊情况已排除,接下来我们可以把问题简单化。

以大圆圆心为原点,两圆圆心连线为x轴重新构造一个坐标系,则大圆坐标为(0,0),小圆坐标为(圆心距离h,0)。

这样计算交点就简单多啦。设第一、二象限的交点坐标为(m,n),则有方程组

①m²+n²=大圆半径c²;②(m-小圆横坐标h)²+n²=小圆半径f².

解得m=(大圆半径c²-小圆半径f²+小圆横坐标h²/(2*小圆横坐标h);

进一步得n=根号(大圆半径c²-m²);{m:=(c*c-f*f+h*h)/2/h;n:=sqrt(c*c-m*m);}

最难的是计算面积。我们把它分成两个弓形计算。大圆上的弓形比较好计算,因为只有一种情况。

扇形面积=大圆面积*((arcsin(交点纵坐标n/大圆半径c)*180/pi*2))/360)=大圆面积*(arcsin(n/c)/pi).

三角型面积=交点纵坐标n*2*交点横坐标m*1/2=n*m.

弓形面积o=扇形面积-三角型面积=c²*pi*(arcsin(n/c)/pi)-n*m.{o:=c*c*pi*(arcsin(n/c)/pi)-n*abs(m)}

小圆所对弓形面积比较难算,因为得分类讨论。先按上述方法算出小圆所对小弓形的面积p。

{p:=f*f*pi*(arcsin(n/f)/pi)-n*abs(h-m);}

接下来要分类讨论:什么时候取小弓形?什么时候取大弓形?

结果是:交点在小圆圆心右侧取大弓形,交点在小圆圆心左侧取小弓形。大家自己画图模拟吧。

{if m>h then p:=f*f*pi-p;}

好了,两个弓形都算好了,加起来就行了。{write(o+p:0:3);}

结束了,希望大家都弄得懂。

喜欢就收藏一下,vic私人qq:1064864324,加我一起讨论问题,一起进步^-^
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: