Re: FPU Control World
- From: "Francois Malan" <Francois.Malan.removeThis@xxxxxxxxxxxxxx>
- Date: 11 Jan 2007 02:15:39 -0800
John Herbster wrote:
"Francois Malan" wrote
... an example I don't understand.
[...]
How can I get this Extended value into a Double
result like the CustomRound routine?
Francois, If you can post a complete short example
with your CustomRound code, then I will look at it.
Regards, JohnH
Hi John
Here is the "manual" routine (it will do a drHalfUp round. x.5 ->
(x+1).0 for positive numbers - or x.y5 -> x.(y+1)0 for 1 decimal place
etc.):
// -------------------------------------------------------------
function TForm1.RoundNumberTo(const Number: Extended; const Decimals:
Integer): Double;
var
I: Integer;
NumberStr: string;
Inverse, TempNum: Extended;
begin
Inverse := Power(10, Decimals);
NumberStr := FloatToStr(Number * Inverse);
if (Pos('E', NumberStr) <> 0) then
NumberStr := FloatToStrF(Number, ffFixed , 18, 18);
I := Pos(DecimalSeparator, NumberStr);
if I = 0 then //Number stays the same
Result := Number
else
begin
TempNum := StrToFloat(Copy(NumberStr, 1, I-1));
if NumberStr[1] = '-' then
begin
if NumberStr[I+1] >= '5' then
Result := (TempNum - 1) / Inverse
else
Result := TempNum / Inverse
end
else
begin
if NumberStr[I+1] < '5' then
Result := TempNum / Inverse
else
Result := (TempNum + 1) / Inverse;
end; //else
end; //else
end;
// -------------------------------------------------------------
In a typical scenario the above function is called 45000+ times and
hence the need to optimize it (otherwise I would have left it as it
generates the exact same rounding as the AS/400 application which we
need to match)
What I did was to add the following code to the above routine:
Var DblNum : Double
....
// at end of routine:
DblNum := DecimalRoundDbl( Number, -Decimals, drHalfUp );
if (DblNum <> Result) then
begin
MessageBox( 0, PChar(FloatToStr(Number) + ' ' +
IntToStr(Decimals)),
'Different Result', 0 );
end;
Examples of numbers that do not seem to "work" (i.e. fails the test if
(Result = DblNum):
Number :0.2918
Decimals :5
Exact :+
0.291,800,000,000,000,059,330,318,435,968,365,520,238,876,342,773,437,5
Manual : 0.2918
Exact :+
0.291,800,000,000,000,059,330,318,435,968,365,520,238,876,342,773,437,5
RoundDbl : 0.2918
Exact :+
0.291,800,000,000,000,003,819,167,204,710,538,499,057,292,938,232,421,87
5
Number :0.6
Decimals :2
Exact :+
0.600,000,000,000,000,088,817,841,970,012,523,233,890,533,447,265,625
Manual : 0.6
Exact :+
0.600,000,000,000,000,088,817,841,970,012,523,233,890,533,447,265,625
RoundDbl : 0.6
Exact :+
0.599,999,999,999,999,977,795,539,507,496,869,191,527,366,638,183,593,75
There are other "better" number that I will post as I find them again -
i have to run many different tests to produce different number sets.
--
.
- Follow-Ups:
- Re: FPU Control World
- From: John Herbster
- Re: FPU Control World
- Prev by Date: Re: Fastcode AnsiStringReplace B&V 2.0.0
- Next by Date: Re: FPU Control World
- Previous by thread: Fastcode SpreadsheetCreator 1.0.0
- Next by thread: Re: FPU Control World
- Index(es):
Relevant Pages
|