Full precision double to string conversion

Stanislav Blinov stanislav.blinov at gmail.com
Sat Nov 3 18:04:07 UTC 2018


On Saturday, 3 November 2018 at 17:26:19 UTC, Ecstatic Coder 
wrote:

>> void main() {
>>     double value = -12.000123456;
>>     int precision = 50;
>>
>>     import std.stdio;
>>     writefln("%.*g", precision, value);
>>
>>     import std.format;
>>     string str = format("%.*g", precision, value);
>>     writeln(str);
>> }
>>
>> Prints:
>>
>> -12.000123456000000743415512260980904102325439453125
>> -12.000123456000000743415512260980904102325439453125
>>
>> That's not quite the -12.000123456 that you'd get from C#'s 
>> ToString().
>
> Unfortunately, but that's still better though, thanks :)

I don't think you understood what I meant. Neither C# nor D 
attempt to exhaust the precision when converting, given default 
arguments. It's merely a matter of those defaults. The snippet 
above obviously provides *more* digits that the default 
.ToString() in C# would.

> But indeed what I really need is a D function which gives a 
> better decimal approximation to the provided double constant, 
> exactly in the same way those in Dart and C# do.
>
> Is there really no such function in D ?

When you call .ToString() in C# with no arguments, it assumes the 
"G" format specifier.

https://docs.microsoft.com/en-us/dotnet/standard/base-types/standard-numeric-format-strings?view=netframework-4.7.2#the-general-g-format-specifier

So for a double, it will use 15-digit precision. D's to!string 
simply uses lower default. If you want the exact same behavior as 
in C#, you can do this:

string toStringLikeInCSharp(double value) {
     import std.format : format;
     return format("%.15G", value);
}

void main() {
     double value = -12.000123456;
     import std.stdio;
     writeln(value.toStringLikeInCSharp); // prints: -12.000123456
}


More information about the Digitalmars-d-learn mailing list