|
Если функция, возвращающая значение типа double, объявлена __fastcall, то Builder возвращает значение в регистрах математического сопроцессора. При этом возвращается не double, а long double. Вроде бы это даже лучше :). Однако это может привести к странным результатам, например:
double __fastcall foo(double v1, double v2)
{
return v1 / v2;
}
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
: TForm(Owner)
{
double v1 = 1.0;
double v2 = 3.0;
double r1 = foo(v1, v2);
if (r1 != foo(v1, v2))
Label1->Caption = "Не может быть";
else
Label1->Caption = "Все в порядке";
}
После первого вызова функции foo() компилятор округляет long double до double и сохраняет в переменной r1. После второго вызова результат long double не приводится к double, а тут же сравнивается в FPU с переменной r1. И если после первого вызова результат округлялся, то получим странный результат. В данном случае (1 / 3) != (1 / 3).
Этого эффекта (скорее дефекта :) можно избежать, если ввести промежуточную переменную:
...
double r2 = foo(v1, v2);
if (r1 != r2)
Label1->Caption = "Не может быть";
else
Label1->Caption = "Все в порядке";
Здесь как раз "Все в порядке".
Такая же ерунда должна быть и с float, кто хочет проверьте.
E-mail: info@telesys.ru