Watch, Follow, &
Connect with Us

Please visit our new home
community.embarcadero.com.


Welcome, Guest
Guest Settings
Help

Thread: EInvalidOp exception when formatting floating-point values


This question is not answered. Helpful answers available: 2. Correct answers available: 1.


Permlink Replies: 0 Threads: [ Previous | Next ]
Martin Nijhoff

Posts: 75
Registered: 8/26/10
EInvalidOp exception when formatting floating-point values  
Click to report abuse...   Click to reply to this thread Reply
  Posted: Oct 13, 2017 7:00 AM
Hi,

I use C++Builder XE6 on Windows 10 version 1703.

I'm having trouble formatting Extended (long double) floating-point values in a 32-bit Windows VCL application.

I've tried a number of functions (Format(), FormatFloat(), FloatToStr(), FloatToStrF(), FloatToText(), ...).
None of these are able to generate non-scientific notation strings with more than 15 digits after the decimal point.

I get the best results with UnicodeString.sprintf().
Unfortunately, UnicodeString.sprintf() throws an EInvalidOp exception ("Invalid floating point operation") for some values.

For example:

Extended Val = Power10(INT64_MAX, -6);
 
Memo->Lines->Add(UnicodeString().sprintf(L"%.0Lf", Val));


To check if UnicodeString.sprintf() is causing the exceptions, I switched to the swprintf_s() API call.
Unfortunately, the exceptions still occur.

To find out which magnitude of values (big/small) cause the exception, I tried this code:

wchar_t Buf[1024];
Extended Val;
 
for (int Power = -18; Power <= 18; Power++)
{
    Val = Power10(INT64_MAX, Power);
 
    try
    {
        swprintf_s(Buf, 1024, L"%.*Lf", (Power < 0 ? -Power : 0), Val);
 
        Memo1->Lines->Add(IntToStr(Power) + ": OK");
    }
    catch (...)
    {
        Memo->Lines->Add(IntToStr(Power) + ": Failed");
    }
}


This produces the following output:

-18: OK
-17: Failed
-16: OK
-15: OK
-14: OK
-13: OK
-12: OK
-11: Failed
-10: OK
-9: OK
-8: Failed
-7: Failed
-6: Failed
-5: OK
-4: OK
-3: OK
-2: OK
-1: OK
0: OK
1: OK
2: OK
3: OK
4: OK
5: OK
6: OK
7: OK
8: Failed
9: OK
10: OK
11: Failed
12: OK
13: OK
14: Failed
15: OK
16: OK
17: Failed
18: OK

When I change the line...

    Val = Power10(INT64_MAX, Power);


...to this...

    Val = Power10(INT64_MAX - 1, Power);


...the EInvalidOp exception is never thrown.

Obviously, writing code that sometimes throws an exception is a no-go for me.

Any ideas what's going on?

--
Martin
Legend
Helpful Answer (5 pts)
Correct Answer (10 pts)

Server Response from: ETNAJIVE02