Предлагаю корректную реализацию функций arcsin(X) и arccos(X), а также функцию вычисления угла по синусу и косинусу либо по длине сторон.
Для того, чтобы функции работали корректно есть ряд констант:
- Код: Выделить всё
var
Matem : packed record
PI, { Число Пи }
PI12, { Число Пи * 1/2 }
PI2, { Число Пи * 2 }
Rad, { Число 180 / Пи }
Q2_2, { Число Корень из 2 / на 2 }
end;
procedure Init;
begin
Matem.PI:=pi; { Число Пи }
Matem.PI12:=pi/2; { Расчет числа Пи * 1/2 }
Matem.PI2:=pi*2; { Расчет числа Пи * 2 }
Matem.Rad:=180/pi; { Расчет числа 180 / Пи }
Matem.Q2_2:=sqrt(2)/2; { Расчет корня из 2 / на 2 }
end;
Ну и, собственно, сами функции:
- Код: Выделить всё
function ArcSin(const X:extended) :extended;
{ вычисление угла в пределах -pi/2<ArcSin(X)<pi/2 }
begin
if abs(X)>Matem.Q2_2
then
begin
if (1-sqr(X))<0
then
ArcSin:=Matem.Pi12*Sign11(X)
else
begin
if X<0
then
ArcSin:=-(Matem.Pi12+ArcTan(sqrt(1-sqr(X))/X))
else
ArcSin:=Matem.Pi12-ArcTan(sqrt(1-sqr(X))/X);
end;
end
else
ArcSin:=ArcTan(X/sqrt(1-sqr(X)));
end;{ArcSin}
{--------------------------------------------------------------------------}
function ArcCos(const X:extended) :extended;
{ вычисление угла в пределах 0<ArcCos(X)<pi }
begin
ArcCos:=Matem.PI12-ArcSin(X);
end;{ArcCos}
{--------------------------------------------------------------------------}
function Ugl(const S,C:extended):extended;
{ вычисление угла в пределах -pi<Ugl(S,C)<pi }
{ S=Sin, C=Cos - входные параметры }
var
F : extended;
begin
if abs(S) > abs(C)
then
begin
F:=C/S;
if F>=0
then
begin
if C>=0
then
begin
if (C=0) and (S<0)
then
Ugl:=-(Matem.PI12+ArcTan(F))
else
Ugl:=Matem.PI12-ArcTan(F);
end
else
begin
if S>=0
then
Ugl:=(Matem.PI12+Matem.PI)-ArcTan(F)
else
Ugl:=-ArcTan(F)-Matem.PI12;
end;
end
else
begin
if C>=0
then
Ugl:=-(Matem.PI12+ArcTan(F))
else
begin
if S>=0
then
Ugl:=Matem.PI12-ArcTan(F)
else
Ugl:=-((Matem.PI12+Matem.PI)+ArcTan(F));
end;
end;
end
else
begin
if C=0
then
Ugl:=0
else
begin
if C>0
then
Ugl:=ArcTan(S/C)
else
begin
if S>=0
then
Ugl:=ArcTan(S/C)+Matem.PI
else
Ugl:=ArcTan(S/C)-Matem.PI
end;
end;
end;
end;{Ugl}
{--------------------------------------------------------------------------}
function Sign11(const X:extended) :extended;
{ возвращает значение '1' со знаком X. Sign11(0)=1 }
{--------------------------------------------------------------------------}
begin
if (X<0) then Sign11:=-1 else Sign11:=1;
end;{Sign11}
Если кому-нибудь пригодятся, буду рад
