Discussion:
[Mingw-w64-public] missing long double format in printf
Jim Michaels
2011-02-22 02:17:48 UTC
Permalink
#include <tr1/stdint.h>
#include <stdio.h>
int main(void) {
int64_t n1=1300000000000LL;
int64_t n2=1999888999256LL;
double
dnum=n1,
dden=n2,
dpercent=n1;
long double
ldnum=n1,
ldden=n2,
ldpercent=n1;

dpercent/=dden;
dpercent*=100;

ldpercent/=ldden;
ldpercent*=100;


printf("n1=%I64d, n2=%I64d\n", n1, n2);
printf("dnum=%g, dden=%g, dpercent=%4.2f", dnum, dden, dpercent);
//printf("ldnum=%Lg, ldden=%Lg, ldpercent=%4.2Lf\n", ldnum, ldden,
ldpercent);//this gives error on the L
printf("ldnum=%lg, ldden=%lg, ldpercent=%4.2lf\n", ldnum, ldden, ldpercent);
//%Lf is a microsoft format and is preferred over %lf for stability.
//should display percentages with 3 places to left, and 2 places to right of
decimal point.
return 0;
}

/*
mingw-test-printf-lf.cpp: In function 'int main()':
mingw-test-printf-lf.cpp:25:79: warning: format '%lg' expects type 'double', but
argument 2 has type 'long double'
mingw-test-printf-lf.cpp:25:79: warning: format '%lg' expects type 'double', but
argument 3 has type 'long double'
mingw-test-printf-lf.cpp:25:79: warning: format '%4.2lf' expects type 'double',
but argument 4 has type 'long double'

so... how to you display a long double in printf????

*/


-------------
Jim Michaels
***@yahoo.com
***@JimsComputerRepairandWebDesign.com
http://JimsComputerRepairandWebDesign.com
http://JesusnJim.com (my personal site, has software)
http://DoLifeComputers.JesusnJim.com (group which I lead)
---
Computer memory/disk size measurements:
[KB KiB] [MB MiB] [GB GiB] [TB TiB]
[10^3B=1,000B=1KB][2^10B=1,024B=1KiB]
[10^6B=1,000,000B=1MB][2^20B=1,048,576B=1MiB]
[10^9B=1,000,000,000B=1GB][2^30B=1,073,741,824B=1GiB]
[10^12B=1,000,000,000,000B=1TB][2^40B=1,099,511,627,776B=1TiB]
Note: disk size is measured in MB, GB, or TB, not in MiB, GiB, or TiB. computer
memory (RAM) is measured in MiB and GiB.
Kai Tietz
2011-02-22 08:54:01 UTC
Permalink
Post by Jim Michaels
#include <tr1/stdint.h>
#include <stdio.h>
int main(void) {
    int64_t n1=1300000000000LL;
    int64_t n2=1999888999256LL;
    double
        dnum=n1,
        dden=n2,
        dpercent=n1;
    long double
        ldnum=n1,
        ldden=n2,
        ldpercent=n1;
    dpercent/=dden;
    dpercent*=100;
    ldpercent/=ldden;
    ldpercent*=100;
    printf("n1=%I64d, n2=%I64d\n", n1, n2);
    printf("dnum=%g, dden=%g, dpercent=%4.2f", dnum, dden, dpercent);
    //printf("ldnum=%Lg, ldden=%Lg, ldpercent=%4.2Lf\n", ldnum, ldden,
ldpercent);//this gives error on the L
    printf("ldnum=%lg, ldden=%lg, ldpercent=%4.2lf\n", ldnum, ldden,
ldpercent);
    //%Lf is a microsoft format and is preferred over %lf for stability.
    //should display percentages with 3 places to left, and 2 places to
right of decimal point.
    return 0;
}
/*
mingw-test-printf-lf.cpp:25:79: warning: format '%lg' expects type 'double',
but argument 2 has type 'long double'
mingw-test-printf-lf.cpp:25:79: warning: format '%lg' expects type 'double',
but argument 3 has type 'long double'
mingw-test-printf-lf.cpp:25:79: warning: format '%4.2lf' expects type
'double', but argument 4 has type 'long double'
so... how to you display a long double in printf????
*/
Hello,

msvcrt's printf/scanf routines don't support 80-bit 'long double'
printing. We introduced for this ISO-C POSIX compatible printf/scanf
routines - wide-character ISO -C printf and ISO-C ascii+wide-character
scanf rountines are just available on mingw-w64's trunk runtime.
You have here two different ways to solve this. You can call directly
the ISO-C printf routines by prefixing the printf/scanf routine by
__mingw_<fct>.
Other way here is to define before including "stdio.h/wchar.h" headers
the macro __USE_MINGW_ANSI_STDIO with value one. If you are using C++
(this is caused by libstdc++ header, which are undefining
macro-replacement of those functions) you need to include here at the
end of include block the mingw-w64 specific header _mingw_print_pop.h
header. This should work too.

I hope it helps,
Kai
NightStrike
2011-02-24 12:50:11 UTC
Permalink
Post by Kai Tietz
Post by Jim Michaels
#include <tr1/stdint.h>
#include <stdio.h>
int main(void) {
    int64_t n1=1300000000000LL;
    int64_t n2=1999888999256LL;
    double
        dnum=n1,
        dden=n2,
        dpercent=n1;
    long double
        ldnum=n1,
        ldden=n2,
        ldpercent=n1;
    dpercent/=dden;
    dpercent*=100;
    ldpercent/=ldden;
    ldpercent*=100;
    printf("n1=%I64d, n2=%I64d\n", n1, n2);
    printf("dnum=%g, dden=%g, dpercent=%4.2f", dnum, dden, dpercent);
    //printf("ldnum=%Lg, ldden=%Lg, ldpercent=%4.2Lf\n", ldnum, ldden,
ldpercent);//this gives error on the L
    printf("ldnum=%lg, ldden=%lg, ldpercent=%4.2lf\n", ldnum, ldden,
ldpercent);
    //%Lf is a microsoft format and is preferred over %lf for stability.
    //should display percentages with 3 places to left, and 2 places to
right of decimal point.
    return 0;
}
/*
mingw-test-printf-lf.cpp:25:79: warning: format '%lg' expects type 'double',
but argument 2 has type 'long double'
mingw-test-printf-lf.cpp:25:79: warning: format '%lg' expects type 'double',
but argument 3 has type 'long double'
mingw-test-printf-lf.cpp:25:79: warning: format '%4.2lf' expects type
'double', but argument 4 has type 'long double'
so... how to you display a long double in printf????
*/
Hello,
msvcrt's printf/scanf routines don't support 80-bit 'long double'
printing. We introduced for this ISO-C POSIX compatible printf/scanf
routines - wide-character ISO -C printf and ISO-C ascii+wide-character
scanf rountines are just available on mingw-w64's trunk runtime.
You have here two different ways to solve this. You can call directly
the ISO-C printf routines by prefixing the printf/scanf routine by
__mingw_<fct>.
Other way here is to define before including "stdio.h/wchar.h" headers
the macro __USE_MINGW_ANSI_STDIO with value one. If you are using C++
(this is caused by libstdc++ header, which are undefining
macro-replacement of those functions) you need to include here at the
end of include block the mingw-w64 specific header _mingw_print_pop.h
header. This should work too.
I hope it helps,
Kai
When you get Kai's suggestion to work, would you mind adding this as a
FAQ in the wiki?
Jim Michaels
2011-03-23 07:09:00 UTC
Permalink
why does ll not work for int64_t and long long (I think) and __int64?

this is quite noticeable. all my programs have to be #ifdef'd.

#if defined(__BORLANDC__)||defined(__MINGW32__)||defined(_MSC_VER)
printf("%I64d", int64_t(2)); //don't try this with ll
#elif defined(__DJGPP__)
printf("%lld", int64_t(2)); //don't try this with ll
#endif

ugh. it would be simpler and shorter if I could simply do __GNUC__ or just use
ll all the time.


the only reason I am posting this back on mingw-w64 mailing list is because the
ifdefs might be useful for someone making portable code.




________________________________
From: Kai Tietz <***@googlemail.com>
To: Jim Michaels <***@yahoo.com>
Sent: Tue, March 22, 2011 12:48:20 AM
Subject: Re: [Mingw-w64-public] missing long double format in printf
if you are using __USE_MINGW_ANSI_STDIO can you still use %I64u?
Well, POSIX equivalent for 'I64' width specifier is 'll'. Btw this is
supported by newer msvcrt-C-runtimes, too. I would recomment not to
use in ISO-C99 variant the width-specifier I64 for compatiblity sake.
You can use here for compatiblity sake inttypes.h header and its
defines to abstract width encoding.

Regards,
Kai
Vincent Torri
2011-03-23 07:56:54 UTC
Permalink
Post by Jim Michaels
why does ll not work for int64_t and long long (I think) and __int64?
this is quite noticeable. all my programs have to be #ifdef'd.
#if defined(__BORLANDC__)||defined(__MINGW32__)||defined(_MSC_VER)
printf("%I64d", int64_t(2)); //don't try this with ll
#elif defined(__DJGPP__)
printf("%lld", int64_t(2)); //don't try this with ll
#endif
ugh. it would be simpler and shorter if I could simply do __GNUC__ or just
use ll all the time.
the only reason I am posting this back on mingw-w64 mailing list is because
the ifdefs might be useful for someone making portable code.
because of the printf behavior on Windows. See

http://msdn.microsoft.com/en-us/library/56e442dc%28v=vs.71%29.aspx

and the links in that page

Vincent Torri
Post by Jim Michaels
------------------------------
*Sent:* Tue, March 22, 2011 12:48:20 AM
*Subject:* Re: [Mingw-w64-public] missing long double format in printf
if you are using __USE_MINGW_ANSI_STDIO can you still use %I64u?
Well, POSIX equivalent for 'I64' width specifier is 'll'. Btw this is
supported by newer msvcrt-C-runtimes, too. I would recomment not to
use in ISO-C99 variant the width-specifier I64 for compatiblity sake.
You can use here for compatiblity sake inttypes.h header and its
defines to abstract width encoding.
Regards,
Kai
------------------------------------------------------------------------------
Enable your software for Intel(R) Active Management Technology to meet the
growing manageability and security demands of your customers. Businesses
are taking advantage of Intel(R) vPro (TM) technology - will your software
be a part of the solution? Download the Intel(R) Manageability Checker
today! http://p.sf.net/sfu/intel-dev2devmar
_______________________________________________
Mingw-w64-public mailing list
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public
James K Beard
2011-03-23 13:31:33 UTC
Permalink
For broadest compatibility I suggest C99 standard, #include <stdint.h> and
ull or ll as the Plan A, and if your compiler doesn't work with that humor
it with an ifdef. The C99 standard works for me for the Linux hosted
cross-compilers.



James K Beard



From: Jim Michaels [mailto:***@yahoo.com]
Sent: Wednesday, March 23, 2011 3:09 AM
To: Kai Tietz; mingw64
Subject: Re: [Mingw-w64-public] missing long double format in printf



why does ll not work for int64_t and long long (I think) and __int64?

this is quite noticeable. all my programs have to be #ifdef'd.

#if defined(__BORLANDC__)||defined(__MINGW32__)||defined(_MSC_VER)
printf("%I64d", int64_t(2)); //don't try this with ll
#elif defined(__DJGPP__)
printf("%lld", int64_t(2)); //don't try this with ll
#endif

ugh. it would be simpler and shorter if I could simply do __GNUC__ or just
use ll all the time.

the only reason I am posting this back on mingw-w64 mailing list is because
the ifdefs might be useful for someone making portable code.



_____

From: Kai Tietz <***@googlemail.com>
To: Jim Michaels <***@yahoo.com>
Sent: Tue, March 22, 2011 12:48:20 AM
Subject: Re: [Mingw-w64-public] missing long double format in printf
if you are using __USE_MINGW_ANSI_STDIO can you still use %I64u?
Well, POSIX equivalent for 'I64' width specifier is 'll'. Btw this is
supported by newer msvcrt-C-runtimes, too. I would recomment not to
use in ISO-C99 variant the width-specifier I64 for compatiblity sake.
You can use here for compatiblity sake inttypes.h header and its
defines to abstract width encoding.

Regards,
Kai

Loading...