Commas in Numbers
From Erlang Community
Problem
You need to format a number for printing with commas (or other locale-dependant marks) in the appropriate places. This is important for creating human-legible print copies of reports.
Solution
Use the Perl-compatible regular expression engine to insert the commas where needed. It's simplest to reverse the string prior to the regexp-pass so that we can hop over any decimal portion. Then reverse the string back on return.
partition_number(Number, Separator) ->
SepChar = hd(Separator),
NumStr = if
is_integer(Number) -> hd(io_lib:format("~B", [Number]));
is_float(Number) -> hd(io_lib:format("~f", [Number]));
true -> Number
end,
% If there is a decimal point, use that as the starting point
{ChgStr, Remain} = case regexp:first_match(NumStr, "\\.") of
{match,Start,Length} ->
{string:substr(NumStr, 1, Start - 1),
string:substr(NumStr,Start,string:len(NumStr))};
nomatch -> {NumStr, ""}
end,
{ok, Subs, _} = regexp:gsub(lists:reverse(ChgStr),
"([0-9][0-9][0-9])", "&" ++ Separator),
Final = case lists:nth(string:len(Subs), Subs) of
SepChar -> string:substr(Subs, 1, string:len(Subs) - 1);
_ -> Subs
end,
lists:reverse(Final) ++ Remain.
|
While this function works, it would be better if it checked for someone passing the separator parameter as a character (rather than a string).
Here's an example of partition_number in action:
1> partition_number(1918928282, ","). "1,918,928,282" 2> partition_number(1982928828, "'"). "1'982'928'828" 3> partition_number(1982928828.12345, "'"). "1'982'928'828.123450" |
In addition to Erlang's various other string-related ills (mainly poor memory and time performance), it has a very limited set of regular expressions. For example, our implementation of partition_number is over twice as long as the [[1][Scheme alternative] because it has no look-ahead (or negative look-ahead) searching functionality.

Digg It
Del.icio.us
Reddit
Facebook
Stumble Upon
Technorati

