Adding a comma into calculated numbers

Aug 27, 2019 at 2:20pm
Hello everyone,
I was writing some code for a C++ class, and I am curious if there is any way to add a comma into your output? For example, let's say one calculates the amount of revenue from a tax percent and a high amount in sales. And let's say the output amount is into the millions. How would I add a comma to separate the digits for easy readability?

Aug 27, 2019 at 2:36pm
One method would be to turn the output value into a string, and then starting at the back, insert a comma every X value (I would guess you'd like very third value, that's quite popular) until you reach the start of the string. Then output the string.

You can get clever with locales - https://stackoverflow.com/questions/7276826/c-format-number-with-commas
Aug 27, 2019 at 2:37pm
Thank you Repeater
Aug 27, 2019 at 2:49pm
Many countries other than the US use period dots or blank spaces instead of commas.

https://docs.oracle.com/cd/E19455-01/806-0169/overview-9/index.html

As Repeater suggested learn to use std::locale, let the compiler do the work for you.

https://en.cppreference.com/w/cpp/locale/locale

Using locale specific formats are best used only when outputting information, otherwise store the data in a "raw" format:

Data files containing locale-specific formats are frequently misinterpreted when transferred to a system in a different locale. For example, a file containing numbers in a French format is not useful to a U.K.-specific program.
Aug 27, 2019 at 2:50pm
Create and imbue a new facet by deriving from std::numpunct<char>.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <iostream>
#include <locale>
#include <string>

struct group_thousands : std::numpunct<char> 
{ std::string do_grouping() const override { return "\3"; } };

int main() 
{
  // NOTE(mbozzi): ownership of the newly-allocated facet is assumed by the library
  // Typically, the following idiom is used:
  std::cout.imbue(std::locale(std::cout.getloc(), new group_thousands));

  // Output might be grouped with a character other than a comma,
  // depending on the current locale
  std::cout << 1234567890ll << '\n'; // 1,234,567,890 
}


Last edited on Aug 27, 2019 at 6:49pm
Aug 27, 2019 at 2:56pm
Hello CodeNovice01,

An option I have found is:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <iostream>
#include <iomanip>
#include <locale>

int main()
{
	std::cout.imbue(std::locale(""));

	std::cout << std::fixed << std::showpoint << std::setprecision(3);

	std::cout << 1234567890.0125 << std::endl;

	std::cout << "\n\n Press Enter to continue: ";
	std::cin.get();

	return 0;
}


Hope that helps,

Andy
Aug 27, 2019 at 3:13pm
@Handy Andy,
that won't work on a system whose's native locale doesn't group by thousands.

For example, on stacked-crooked.com, to get the expected output, I need to override the locale category to something that separates thousands by default. I can do this by setting the environment variable LC_ALL to en_US.utf8, for example.

The plain-old C locale (the default setting on that service) will not yield the expected output:
http://coliru.stacked-crooked.com/a/2116d3e07f83e963

Not to say this isn't a good option. The locale is left in the user's control. It's just not guaranteed to get a comma-separated output.
Last edited on Aug 27, 2019 at 3:20pm
Aug 27, 2019 at 4:31pm
@mbozzi,

Thank you for the input.

In my haste and lack of knowledge of what other countries do I did not consider that problem.

In my defense maybe I read to much into OP question and figured this would work.

In the future I will present it differently.

Andy
Aug 27, 2019 at 7:05pm
@Handy Andy, I believe that using the native locale is in many cases the best choice for data being presented to the user. In fact, yours might be the best suggestion:

If OP wants to view localized output, they can adjust the native locale to one that provides it by default.

@Furry Guy has it right to suggest using the classic locale for data that's going to be processed by another computer program.
Last edited on Aug 27, 2019 at 7:09pm
Topic archived. No new replies allowed.