[题意]
给定四面体的四个顶点,求内切球的球心和半径
若内切球不存在,输出”O O O O”
[分析]
各种公式~
设四面体四个顶点坐标分别为
(xi,yi,zi)
,与之相对的面的面积为
si
,四面体体积为
V
,则有
四面体内心(内切球球心)坐标
四面体内切球半径
r = 3Vs1+s2+s3+s4
面积可以用三维叉积求,体积则用混合积
若体积为0,则内切球不存在
[代码]
#include <bits/stdc++.h>
using namespace std ;
const int N = 1e5 ;
typedef long long LL ;
int T ;
double sa , sb , sc , sd , v ;
double s , r , x , y , z ;
struct point
{
double x , y , z ;
point( double x = 0 , double y = 0 , double z = 0 ):x(x),y(y),z(z) { }
int read() { return scanf( "%lf%lf%lf" , &x , &y , &z ) ; }
double length() { return sqrt(x*x+y*y+z*z) ; }
} A , B , C , D ;
point operator - ( point A , point B )
{
return point( A.x-B.x , A.y-B.y , A.z-B.z ) ;
}
double dot( point A , point B )
{
return A.x*B.x + A.y*B.y + A.z*B.z ;
}
point cross( point A , point B )
{
return point( A.y*B.z-A.z*B.y , A.z*B.x-A.x*B.z , A.x*B.y-A.y*B.x ) ;
}
double area( point A , point B , point C )
{
return cross(B-A,C-A).length()/2 ;
}
double volume( point A , point B , point C , point D )
{
return fabs(dot(D-A,cross(B-A,C-A)))/6 ;
}
int main()
{
while( ~A.read() )
{
B.read() ;
C.read() ;
D.read() ;
sa = area(B,C,D) ;
sb = area(A,C,D) ;
sc = area(A,B,D) ;
sd = area(A,B,C) ;
v = volume(A,B,C,D) ;
if( v < 1e-8 )
{
puts("O O O O") ;
continue ;
}
else
{
s = sa+sb+sc+sd ;
r = v*3/s ;
x = (A.x*sa+B.x*sb+C.x*sc+D.x*sd)/s ;
y = (A.y*sa+B.y*sb+C.y*sc+D.y*sd)/s ;
z = (A.z*sa+B.z*sb+C.z*sc+D.z*sd)/s ;
printf( "%.4f %.4f %.4f %.4f\n" , x , y , z , r ) ;
}
}
return 0 ;
}