views:

2748

answers:

5

I'd like to group the digits in a double by thousands, but also output however number of decimals are actually in the number. I cannot figure out the format string.

 1000 => 1,000
 100000 => 100,000
 123.456 => 123.456
 100000.21 => 100,000.21
 100200.123456 => 100,200.123456

Disclaimers (it's not as straightforward as you think):

  • Please do not point me to this question it does not answer my question
  • Please do not point me to MSDN, the articles have not helped me. (If you believe I'm reading them incorrectly, read them yourself and post the correct answer)
  • .toString("n") does not work, it rounds the digits
A: 

Try this one:

VB:

Dim vals() As Double = {1000, 100000, 123.456, 100000.21, 100200.123456}
For Each val As Double in vals
   Console.WriteLine(val.ToString("###,###.#########"))
Next val

C#:

double[] vals = new double[] {1000, 100000, 123.456, 100000.21, 100200.123456};
foreach (double val in vals)
{
    Console.WriteLine(val.ToString("###,###.#########"));
}

The problem is that there is no format to handle an arbitrary number of decimals. However, since you can only store a very limited precision, you can just use that and add a few more # characters as needed to cover it, assuming you're willing to let it cut off any insignificant 0's.

And the MSDN link you posted is the exact place you'd go to read how to do this.

Joel Coehoorn
Ah- the N format doesn't handle decimals like I thought. Gimme a minute and I'll fix it.
Joel Coehoorn
+6  A: 

This appears to do exactly what you want:

public void Code(params string[] args)
{
 Print(1000);
 Print(100000);
 Print(123.456);
 Print(100000.21 );
 Print(100200.123456);
}

void Print(double n)
{
 Console.WriteLine("{0:###,###.#######}", n);
}

1,000
100,000
123.456
100,000.21
100,200.123456
James Curran
If you have more than 7 decimal places, won't that truncate it?
MusiGenesis
It appears so, which is less than ideal, but I can push it out to 12 decimal places which should be a limit for my purposes.
Tom Ritter
Won't work for an arbitrary number of decimals, though. Since double has precision of 15-16 digits, though "{0:##,###,###,###,###,##0.###############}" would seem to capture all possible doubles with all possible digits. Notice I prefer a leading 0.
tvanfosson
+1  A: 

Try simply use "#,#", this adds the commas for thousands et al, but I don't know if it will keep the decimals, otherwise "#,###.####################", or any number of '#' symbols that you want after the decimal.

dragonjujo
A: 

You can create a custom format string .ToString("###,###.######") Custom Numeric Format Strings

Aaron Fischer
A: 

This could be a little slow, but it will do what you want.

public static string FormatNumber(double num)
{
    string s = num.ToString();
    string result = "";

    if(s.IndexOf('.') != -1)
    {
     result = s.Substring(s.IndexOf('.'));
     s = s.Substring(0, s.IndexOf('.'));
    }

    while (s.Length > 3)
    {
     result = "," + s.Substring(s.Length - 3);
     s = s.Substring(0, s.Length - 3);
    }
    if (s.Length == 0)
     return result.Substring(1);
    return s + result;
}
Jason Lepack
Downvoting is a little harsh for something that answers the question no? While it's not the best solution, it is a solution.
Jason Lepack