File Coverage

blib/lib/Number/Format.pm
Criterion Covered Total %
statement 287 298 96.3
branch 187 224 83.4
condition 43 64 67.1
subroutine 20 20 100.0
pod 8 8 100.0
total 545 614 88.7


line stmt bran cond sub pod time code
1             package Number::Format 1.77; # TRIAL
2              
3             # ABSTRACT: Perl extension for formatting numbers
4              
5             # Minimum version is 5.10.0. May work on earlier versions, but not
6             # supported on any version older than 5.10. Hack this line at your own risk:
7             require 5.010;
8              
9 9     9   1087006 use strict;
  9         20  
  9         476  
10 9     9   46 use warnings;
  9         17  
  9         886  
11              
12             #pod =head1 SYNOPSIS
13             #pod
14             #pod use Number::Format;
15             #pod my $x = Number::Format->new(%args);
16             #pod $formatted = $x->round($number, $precision);
17             #pod $formatted = $x->format_number($number, $precision, $trailing_zeroes);
18             #pod $formatted = $x->format_negative($number, $picture);
19             #pod $formatted = $x->format_picture($number, $picture);
20             #pod $formatted = $x->format_price($number, $precision, $symbol);
21             #pod $formatted = $x->format_bytes($number, $precision);
22             #pod $number = $x->unformat_number($formatted);
23             #pod
24             #pod use Number::Format qw(:subs);
25             #pod $formatted = round($number, $precision);
26             #pod $formatted = format_number($number, $precision, $trailing_zeroes);
27             #pod $formatted = format_negative($number, $picture);
28             #pod $formatted = format_picture($number, $picture);
29             #pod $formatted = format_price($number, $precision, $symbol);
30             #pod $formatted = format_bytes($number, $precision);
31             #pod $number = unformat_number($formatted);
32             #pod
33             #pod =head1 DESCRIPTION
34             #pod
35             #pod These functions provide an easy means of formatting numbers in a
36             #pod manner suitable for displaying to the user.
37             #pod
38             #pod There are two ways to use this package. One is to declare an object
39             #pod of type Number::Format, which you can think of as a formatting engine.
40             #pod The various functions defined here are provided as object methods.
41             #pod The constructor C can be used to set the parameters of the
42             #pod formatting engine. Valid parameters are:
43             #pod
44             #pod THOUSANDS_SEP - character inserted between groups of 3 digits
45             #pod DECIMAL_POINT - character separating integer and fractional parts
46             #pod MON_THOUSANDS_SEP - like THOUSANDS_SEP, but used for format_price
47             #pod MON_DECIMAL_POINT - like DECIMAL_POINT, but used for format_price
48             #pod INT_CURR_SYMBOL - character(s) denoting currency (see format_price())
49             #pod DECIMAL_DIGITS - number of digits to the right of dec point (def 2)
50             #pod DECIMAL_FILL - boolean; whether to add zeroes to fill out decimal
51             #pod NEG_FORMAT - format to display negative numbers (def ``-x'')
52             #pod KILO_SUFFIX - suffix to add when format_bytes formats kilobytes (trad)
53             #pod MEGA_SUFFIX - " " " " " " megabytes (trad)
54             #pod GIGA_SUFFIX - " " " " " " gigabytes (trad)
55             #pod TERA_SUFFIX - " " " " " " terabytes (trad)
56             #pod KIBI_SUFFIX - suffix to add when format_bytes formats kibibytes (iec)
57             #pod MEBI_SUFFIX - " " " " " " mebibytes (iec)
58             #pod GIBI_SUFFIX - " " " " " " gibibytes (iec)
59             #pod TEBI_SUFFIX - " " " " " " tebibytes (iec)
60             #pod
61             #pod They may be specified in upper or lower case, with or without a
62             #pod leading hyphen ( - ).
63             #pod
64             #pod If C is set to the empty string, format_number will not
65             #pod insert any separators.
66             #pod
67             #pod The defaults for C, C,
68             #pod C, C, and C
69             #pod come from the POSIX locale information (see L). If your
70             #pod POSIX locale does not provide C and/or
71             #pod C fields, then the C and/or
72             #pod C values are used for those parameters. Formerly,
73             #pod POSIX was optional but this caused problems in some cases, so it is
74             #pod now required. If this causes you hardship, please contact the author
75             #pod of this package at (remove "SPAM" to get correct
76             #pod email address) for help.
77             #pod
78             #pod If any of the above parameters are not specified when you invoke
79             #pod C, then the values are taken from package global variables of
80             #pod the same name (e.g. C<$DECIMAL_POINT> is the default for the
81             #pod C parameter). If you use the C<:vars> keyword on your
82             #pod C line (see non-object-oriented example below) you
83             #pod will import those variables into your namesapce and can assign values
84             #pod as if they were your own local variables. The default values for all
85             #pod the parameters are:
86             #pod
87             #pod THOUSANDS_SEP = ','
88             #pod DECIMAL_POINT = '.'
89             #pod MON_THOUSANDS_SEP = ','
90             #pod MON_DECIMAL_POINT = '.'
91             #pod INT_CURR_SYMBOL = 'USD'
92             #pod DECIMAL_DIGITS = 2
93             #pod DECIMAL_FILL = 0
94             #pod NEG_FORMAT = '-x'
95             #pod KILO_SUFFIX = 'K'
96             #pod MEGA_SUFFIX = 'M'
97             #pod GIGA_SUFFIX = 'G'
98             #pod TERA_SUFFIX = 'T'
99             #pod KIBI_SUFFIX = 'KiB'
100             #pod MEBI_SUFFIX = 'MiB'
101             #pod GIBI_SUFFIX = 'GiB'
102             #pod TEBI_SUFFIX = 'TiB'
103             #pod
104             #pod Note however that when you first call one of the functions in this
105             #pod module I using the object-oriented interface, further setting
106             #pod of those global variables will have no effect on non-OO calls. It is
107             #pod recommended that you use the object-oriented interface instead for
108             #pod fewer headaches and a cleaner design.
109             #pod
110             #pod The C and C values are not set by the
111             #pod Locale system, but are definable by the user. They affect the output
112             #pod of C. Setting C is like giving that
113             #pod value as the C<$precision> argument to that function. Setting
114             #pod C to a true value causes C to append
115             #pod zeroes to the right of the decimal digits until the length is the
116             #pod specified number of digits.
117             #pod
118             #pod C is only used by C and is a string
119             #pod containing the letter 'x', where that letter will be replaced by a
120             #pod positive representation of the number being passed to that function.
121             #pod C and C utilize this feature by
122             #pod calling C if the number was less than 0.
123             #pod
124             #pod C, C, C, and C are
125             #pod used by C when the value is over 1024, 1024**2, 1024**3,
126             #pod or 1024**4, respectively. The default values are "K", "M", "G", and
127             #pod "T". These apply in the default "traditional" mode only.
128             #pod
129             #pod C, C, C, and C are
130             #pod used by C when the value is over 1024, 1024**2,
131             #pod 1024**3, or 1024**4, respectively. The default values are "KiB", "MiB",
132             #pod "GiB", "TiB". These apply in the "iso60027" mode only.
133             #pod
134             #pod The only restrictions on C and C are that
135             #pod they must not be digits and must not be identical. There are no
136             #pod restrictions on C.
137             #pod
138             #pod For example, a German user might include this in their code:
139             #pod
140             #pod use Number::Format;
141             #pod my $de = Number::Format->new(-thousands_sep => '.',
142             #pod -decimal_point => ',',
143             #pod -int_curr_symbol => 'DEM');
144             #pod my $formatted = $de->format_number($number);
145             #pod
146             #pod Or, if you prefer not to use the object oriented interface, you can do
147             #pod this instead:
148             #pod
149             #pod use Number::Format qw(:subs :vars);
150             #pod $THOUSANDS_SEP = '.';
151             #pod $DECIMAL_POINT = ',';
152             #pod $INT_CURR_SYMBOL = 'DEM';
153             #pod my $formatted = format_number($number);
154             #pod
155             #pod =head1 EXPORTS
156             #pod
157             #pod Nothing is exported by default. To export the functions or the global
158             #pod variables defined herein, specify the function name(s) on the import
159             #pod list of the C statement. To export all functions
160             #pod defined herein, use the special tag C<:subs>. To export the
161             #pod variables, use the special tag C<:vars>; to export both subs and vars
162             #pod you can use the tag C<:all>.
163             #pod
164             #pod =cut
165              
166             ###---------------------------------------------------------------------
167              
168 9     9   66 use Exporter;
  9         36  
  9         413  
169 9     9   42 use Carp;
  9         24  
  9         547  
170 9     9   415 use POSIX qw(localeconv);
  9         6865  
  9         52  
171 9     9   4961 use base qw(Exporter);
  9         16  
  9         6606  
172              
173             our @EXPORT_SUBS =
174             qw( format_number format_negative format_picture
175             format_price format_bytes round unformat_number );
176              
177             our @EXPORT_LC_NUMERIC =
178             qw( $DECIMAL_POINT $THOUSANDS_SEP $GROUPING );
179              
180             our @EXPORT_LC_MONETARY =
181             qw( $INT_CURR_SYMBOL $CURRENCY_SYMBOL $MON_DECIMAL_POINT
182             $MON_THOUSANDS_SEP $MON_GROUPING $POSITIVE_SIGN $NEGATIVE_SIGN
183             $INT_FRAC_DIGITS $FRAC_DIGITS $P_CS_PRECEDES $P_SEP_BY_SPACE
184             $N_CS_PRECEDES $N_SEP_BY_SPACE $P_SIGN_POSN $N_SIGN_POSN );
185              
186             our @EXPORT_OTHER =
187             qw( $DECIMAL_DIGITS $DECIMAL_FILL $NEG_FORMAT
188             $KILO_SUFFIX $MEGA_SUFFIX $GIGA_SUFFIX $TERA_SUFFIX
189             $KIBI_SUFFIX $MEBI_SUFFIX $GIBI_SUFFIX $TEBI_SUFFIX);
190              
191             our @EXPORT_VARS = ( @EXPORT_LC_NUMERIC, @EXPORT_LC_MONETARY, @EXPORT_OTHER );
192             our @EXPORT_ALL = ( @EXPORT_SUBS, @EXPORT_VARS );
193              
194             our @EXPORT_OK = ( @EXPORT_ALL );
195              
196             our %EXPORT_TAGS = ( subs => \@EXPORT_SUBS,
197             vars => \@EXPORT_VARS,
198             lc_numeric_vars => \@EXPORT_LC_NUMERIC,
199             lc_monetary_vars => \@EXPORT_LC_MONETARY,
200             other_vars => \@EXPORT_OTHER,
201             all => \@EXPORT_ALL );
202              
203             # Refer to http://www.opengroup.org/onlinepubs/007908775/xbd/locale.html
204             # for more details about the POSIX variables
205              
206             # Locale variables provided by POSIX for numbers (LC_NUMERIC)
207             our $DECIMAL_POINT = '.'; # decimal point symbol for numbers
208             our $THOUSANDS_SEP = ','; # thousands separator for numbers
209             our $GROUPING = undef;# grouping rules for thousands (UNSUPPORTED)
210              
211             # Locale variables provided by POSIX for currency (LC_MONETARY)
212             our $INT_CURR_SYMBOL = 'USD';# intl currency symbol
213             our $CURRENCY_SYMBOL = '$'; # domestic currency symbol
214             our $MON_DECIMAL_POINT = '.'; # decimal point symbol for monetary values
215             our $MON_THOUSANDS_SEP = ','; # thousands separator for monetary values
216             our $MON_GROUPING = undef;# like 'grouping' for monetary (UNSUPPORTED)
217             our $POSITIVE_SIGN = ''; # string to add for non-negative monetary
218             our $NEGATIVE_SIGN = '-'; # string to add for negative monetary
219             our $INT_FRAC_DIGITS = 2; # digits to right of decimal for intl currency
220             our $FRAC_DIGITS = 2; # digits to right of decimal for currency
221             our $P_CS_PRECEDES = 1; # curr sym precedes(1) or follows(0) positive
222             our $P_SEP_BY_SPACE = 1; # add space to positive; 0, 1, or 2
223             our $N_CS_PRECEDES = 1; # curr sym precedes(1) or follows(0) negative
224             our $N_SEP_BY_SPACE = 1; # add space to negative; 0, 1, or 2
225             our $P_SIGN_POSN = 1; # sign rules for positive: 0-4
226             our $N_SIGN_POSN = 1; # sign rules for negative: 0-4
227              
228             # The following are specific to Number::Format
229             our $DECIMAL_DIGITS = 2;
230             our $DECIMAL_FILL = 0;
231             our $NEG_FORMAT = '-x';
232             our $KILO_SUFFIX = 'K';
233             our $MEGA_SUFFIX = 'M';
234             our $GIGA_SUFFIX = 'G';
235             our $TERA_SUFFIX = 'T';
236             our $KIBI_SUFFIX = 'KiB';
237             our $MEBI_SUFFIX = 'MiB';
238             our $GIBI_SUFFIX = 'GiB';
239             our $TEBI_SUFFIX = 'TiB';
240              
241             our $DEFAULT_LOCALE = { (
242             # LC_NUMERIC
243             decimal_point => $DECIMAL_POINT,
244             thousands_sep => $THOUSANDS_SEP,
245             grouping => $GROUPING,
246              
247             # LC_MONETARY
248             int_curr_symbol => $INT_CURR_SYMBOL,
249             currency_symbol => $CURRENCY_SYMBOL,
250             mon_decimal_point => $MON_DECIMAL_POINT,
251             mon_thousands_sep => $MON_THOUSANDS_SEP,
252             mon_grouping => $MON_GROUPING,
253             positive_sign => $POSITIVE_SIGN,
254             negative_sign => $NEGATIVE_SIGN,
255             int_frac_digits => $INT_FRAC_DIGITS,
256             frac_digits => $FRAC_DIGITS,
257             p_cs_precedes => $P_CS_PRECEDES,
258             p_sep_by_space => $P_SEP_BY_SPACE,
259             n_cs_precedes => $N_CS_PRECEDES,
260             n_sep_by_space => $N_SEP_BY_SPACE,
261             p_sign_posn => $P_SIGN_POSN,
262             n_sign_posn => $N_SIGN_POSN,
263              
264             # The following are specific to Number::Format
265             decimal_digits => $DECIMAL_DIGITS,
266             decimal_fill => $DECIMAL_FILL,
267             neg_format => $NEG_FORMAT,
268             kilo_suffix => $KILO_SUFFIX,
269             mega_suffix => $MEGA_SUFFIX,
270             giga_suffix => $GIGA_SUFFIX,
271             tera_suffix => $TERA_SUFFIX,
272             kibi_suffix => $KIBI_SUFFIX,
273             mebi_suffix => $MEBI_SUFFIX,
274             gibi_suffix => $GIBI_SUFFIX,
275             tebi_suffix => $TEBI_SUFFIX,
276             ) };
277              
278             #
279             # POSIX::localeconv() returns -1 for numeric values that are not applicable to
280             # the current locale. This module ignores them. @IGNORE_NEGATIVE lists the
281             # ones that this module otherwise handles (there are some fields that this
282             # module always ignores, so don't need to be in the list). (Prior to v5.37.7,
283             # only the Windows version of POSIX::localeconv() returned -1; other versions
284             # simply didn't return any values at all for not-applicable fields. But the
285             # end result is the same regardless of version.)
286              
287             #
288             our @IGNORE_NEGATIVE = qw( frac_digits int_frac_digits
289             n_cs_precedes n_sep_by_space n_sign_posn
290             p_xs_precedes p_sep_by_space p_sign_posn );
291              
292             #
293             # Largest integer a 32-bit Perl can handle is based on the mantissa
294             # size of a double float, which is up to 53 bits. While we may be
295             # able to support larger values on 64-bit systems, some Perl integer
296             # operations on 64-bit integer systems still use the 53-bit-mantissa
297             # double floats. To be safe, we cap at 2**53; use Math::BigFloat
298             # instead for larger numbers.
299             #
300 9     9   67 use constant MAX_INT => 2**53;
  9         13  
  9         4878  
301              
302             ###---------------------------------------------------------------------
303              
304             # INTERNAL FUNCTIONS
305              
306             # These functions (with names beginning with '_' are for internal use
307             # only. There is no guarantee that they will remain the same from one
308             # version to the next!
309              
310             ##----------------------------------------------------------------------
311              
312             # _get_self creates an instance of Number::Format with the default
313             # values for the configuration parameters, if the first element of
314             # @_ is not already an object.
315              
316             my $DefaultObject;
317             sub _get_self
318             {
319             # Not calling $_[0]->isa because that may result in unblessed
320             # reference error
321 342 100 66 342   1378 unless (ref $_[0] && UNIVERSAL::isa($_[0], "Number::Format"))
322             {
323 70   66     231 $DefaultObject ||= Number::Format->new();
324 70         223 unshift (@_, $DefaultObject);
325             }
326 342         846 @_;
327             }
328              
329             ##----------------------------------------------------------------------
330              
331             # _check_seps is used to validate that the thousands_sep,
332             # decimal_point, mon_thousands_sep and mon_decimal_point variables
333             # have acceptable values. For internal use only.
334              
335             sub _check_seps
336             {
337 132     132   197 my ($self) = @_;
338 132 50       258 croak "Not an object" unless ref $self;
339 132         234 foreach my $prefix ("", "mon_")
340             {
341             croak "${prefix}thousands_sep is undefined"
342 264 50       589 unless defined $self->{"${prefix}thousands_sep"};
343             croak "${prefix}thousands_sep may not be numeric"
344 264 50       750 if $self->{"${prefix}thousands_sep"} =~ /\d/;
345             croak "${prefix}decimal_point may not be numeric"
346 264 50       581 if $self->{"${prefix}decimal_point"} =~ /\d/;
347             croak("${prefix}thousands_sep and ".
348             "${prefix}decimal_point may not be equal")
349             if $self->{"${prefix}decimal_point"} eq
350             $self->{"${prefix}thousands_sep"}
351              
352             # There are legal locales where 'mon_decimal_point' and
353             # 'mon_thousands_sep' are both "" (the empty string)
354 264 0 0     688 && ($prefix eq "" || $self->{"mon_decimal_point"} ne "");
      33        
355             }
356             }
357              
358             ##----------------------------------------------------------------------
359              
360             # _get_multipliers returns the multipliers to be used for kilo, mega,
361             # giga, and tera (un-)formatting. Used in format_bytes and unformat_number.
362             # For internal use only.
363              
364             sub _get_multipliers
365             {
366 43     43   97 my($base) = @_;
367 43 100 100     158 if (!defined($base) || $base == 1024)
    100          
368             {
369             # the "tera" value is not portable, but that's a matter for the caller
370 9     9   75 no warnings 'portable';
  9         22  
  9         35458  
371 34         159 return ( kilo => 0x00000000400,
372             mega => 0x00000100000,
373             giga => 0x00040000000,
374             tera => 0x10000000000);
375             }
376             elsif ($base == 1000)
377             {
378 4         20 return ( kilo => 1_000,
379             mega => 1_000_000,
380             giga => 1_000_000_000,
381             tera => 1_000_000_000_000 );
382             }
383             else
384             {
385 5 100       263 croak "base overflow" if $base **3 > MAX_INT;
386 4 100 100     501 croak "base must be a positive integer"
387             unless $base > 0 && $base == int($base);
388 1         7 return ( kilo => $base,
389             mega => $base ** 2,
390             giga => $base ** 3,
391             tera => $base ** 4);
392             }
393             }
394              
395             ##----------------------------------------------------------------------
396              
397             # _complain_undef displays a warning message on STDERR and is called
398             # when a subroutine has been invoked with an undef value. A warning
399             # message is printed if the calling environment has "uninitialized"
400             # warnings enabled.
401              
402             sub _complain_undef
403             {
404 8     8   15 my @stack;
405 8         52 my($sub, $bitmask) = (caller(1))[3,9];
406 8         34 my $offset = $warnings::Offsets{"uninitialized"};
407 8 100       1378 carp "Use of uninitialized value in call to $sub"
408             if vec($bitmask, $offset, 1);
409             }
410              
411             ##----------------------------------------------------------------------
412              
413             #pod =method new
414             #pod
415             #pod my $formatter = Number::Format->new( %args );
416             #pod
417             #pod Creates a new Number::Format object. Valid keys for %args are any of
418             #pod the parameters described above. Keys may be in all uppercase or all
419             #pod lowercase, and may optionally be preceded by a hyphen (-) character.
420             #pod Example:
421             #pod
422             #pod my $de = Number::Format->new(-thousands_sep => '.',
423             #pod -decimal_point => ',',
424             #pod -int_curr_symbol => 'DEM');
425             #pod
426             #pod =cut
427              
428             sub new
429             {
430 12     12 1 1571938 my $type = shift;
431 12         66 my %args = @_;
432              
433             # Fetch defaults from current locale, or failing that, using globals
434 12         30 my $me = {};
435             # my $locale = setlocale(LC_ALL, "");
436 12         259 my $locale_values = localeconv();
437              
438             # Strip out illegal negative values from the current locale
439 12         52 foreach ( @IGNORE_NEGATIVE )
440             {
441 96 100 66     362 if (defined($locale_values->{$_}) && $locale_values->{$_} eq '-1')
442             {
443 84         175 delete $locale_values->{$_};
444             }
445             }
446              
447 12         106 while(my($arg, $default) = each %$DEFAULT_LOCALE)
448             {
449             $me->{$arg} = (( exists $locale_values->{$arg})
450             && $locale_values->{$arg} ne "")
451 348 100 100     1041 ? $locale_values->{$arg}
452             : $default;
453              
454 348         671 foreach ($arg, uc $arg, "-$arg", uc "-$arg")
455             {
456 1352 100       3064 next unless defined $args{$_};
457 40         53 $me->{$arg} = $args{$_};
458 40         68 delete $args{$_};
459 40         95 last;
460             }
461             }
462              
463             #
464             # Some locales set the decimal_point to "," and the thousands_sep to "".
465             # This module generally defaults an empty thousands_sep to ",", creating a
466             # conflict in such a locale. Instead, leave the thousands_sep as the
467             # empty string. Suggested by Moritz Onken.
468 12         33 foreach my $prefix ("", "mon_")
469             {
470             $me->{"${prefix}thousands_sep"} = ""
471             if ($me->{"${prefix}decimal_point"} eq
472 24 50       104 $me->{"${prefix}thousands_sep"});
473             }
474              
475 12 50       42 croak "Invalid argument(s)" if %args;
476 12         33 bless $me, $type;
477 12         122 $me;
478             }
479              
480             ##----------------------------------------------------------------------
481              
482             #pod =method round
483             #pod
484             #pod my $str = $formatter->($number, $precision);
485             #pod
486             #pod Rounds the number to the specified precision. If C<$precision> is
487             #pod omitted, the value of the C parameter is used (default
488             #pod value 2). Both input and output are numeric (the function uses math
489             #pod operators rather than string manipulation to do its job), The value of
490             #pod C<$precision> may be any integer, positive or negative. Examples:
491             #pod
492             #pod round(3.14159) yields 3.14
493             #pod round(3.14159, 4) yields 3.1416
494             #pod round(42.00, 4) yields 42
495             #pod round(1234, -2) yields 1200
496             #pod
497             #pod Since this is a mathematical rather than string oriented function,
498             #pod there will be no trailing zeroes to the right of the decimal point,
499             #pod and the C and C variables are ignored.
500             #pod To format your number using the C and C
501             #pod variables, use C instead.
502             #pod
503             #pod =cut
504              
505             sub round
506             {
507 125     125 1 274354 my ($self, $number, $precision) = _get_self @_;
508              
509 125 100       227 unless (defined($number))
510             {
511 1         4 _complain_undef();
512 1         6 $number = 0;
513             }
514              
515 125 100       188 $precision = $self->{decimal_digits} unless defined $precision;
516 125 50       200 $precision = 2 unless defined $precision;
517              
518 125 50       199 croak("precision must be integer")
519             unless int($precision) == $precision;
520              
521 125 50 33     234 if (ref($number) && $number->isa("Math::BigFloat"))
522             {
523 0         0 my $rounded = $number->copy();
524 0         0 $rounded->precision(-$precision);
525 0         0 return $rounded;
526             }
527              
528 125         157 my $sign = $number <=> 0;
529 125         224 my $multiplier = (10 ** $precision);
530 125         155 my $result = abs($number);
531 125         194 my $product = $result * $multiplier;
532              
533 125 100       520 croak "round() overflow. Try smaller precision or use Math::BigFloat"
534             if $product > MAX_INT;
535              
536             # We need to add 1e-14 to avoid some rounding errors due to the
537             # way floating point numbers work - see string-eq test in t/round.t
538 124         224 $result = int($product + .5 + 1e-14) / $multiplier;
539 124 100       184 $result = -$result if $sign < 0;
540 124         244 return $result;
541             }
542              
543             ##----------------------------------------------------------------------
544              
545             #pod =method format_number
546             #pod
547             #pod my $str = $formatter->format_number($number, $precision, $trailing_zeroes);
548             #pod
549             #pod Formats a number by adding C between each set of 3
550             #pod digits to the left of the decimal point, substituting C
551             #pod for the decimal point, and rounding to the specified precision using
552             #pod C. Note that C<$precision> is a I precision
553             #pod specifier; trailing zeroes will only appear in the output if
554             #pod C<$trailing_zeroes> is provided, or the parameter C is
555             #pod set, with a value that is true (not zero, undef, or the empty string).
556             #pod If C<$precision> is omitted, the value of the C
557             #pod parameter (default value of 2) is used.
558             #pod
559             #pod If the value is too large or great to work with as a regular number,
560             #pod but instead must be shown in scientific notation, returns that number
561             #pod in scientific notation without further formatting.
562             #pod
563             #pod Examples:
564             #pod
565             #pod format_number(12345.6789) yields '12,345.68'
566             #pod format_number(123456.789, 2) yields '123,456.79'
567             #pod format_number(1234567.89, 2) yields '1,234,567.89'
568             #pod format_number(1234567.8, 2) yields '1,234,567.8'
569             #pod format_number(1234567.8, 2, 1) yields '1,234,567.80'
570             #pod format_number(1.23456789, 6) yields '1.234568'
571             #pod format_number("0.000020000E+00", 7);' yields '2e-05'
572             #pod
573             #pod Of course the output would have your values of C and
574             #pod C instead of ',' and '.' respectively.
575             #pod
576             #pod =cut
577              
578             sub format_number
579             {
580 96     96 1 340793 my ($self, $number, $precision, $trailing_zeroes, $mon) = _get_self @_;
581              
582 96 100       171 unless (defined($number))
583             {
584 2         7 _complain_undef();
585 2         8 $number = 0;
586             }
587              
588 96         233 $self->_check_seps(); # first make sure the SEP variables are valid
589              
590             my($thousands_sep, $decimal_point) =
591             $mon ? @$self{qw(mon_thousands_sep mon_decimal_point)}
592 96 100       250 : @$self{qw(thousands_sep decimal_point)};
593              
594             # Set defaults and standardize number
595 96 100       163 $precision = $self->{decimal_digits} unless defined $precision;
596 96 100       172 $trailing_zeroes = $self->{decimal_fill} unless defined $trailing_zeroes;
597              
598             # Handle negative numbers
599 96         143 my $sign = $number <=> 0;
600 96 100       139 $number = abs($number) if $sign < 0;
601 96         181 $number = $self->round($number, $precision); # round off $number
602              
603             # detect scientific notation
604 95         108 my $exponent = 0;
605 95 50       506 if ($number =~ /^(-?[\d.]+)e([+-]\d+)$/)
606             {
607             # Don't attempt to format numbers that require scientific notation.
608 0         0 return $number;
609             }
610              
611             # Split integer and decimal parts of the number and add commas
612 95         154 my $integer = int($number);
613 95         95 my $decimal;
614              
615             # Note: In perl 5.6 and up, string representation of a number
616             # automagically includes the locale decimal point. This way we
617             # will detect the decimal part correctly as long as the decimal
618             # point is 1 character.
619 95 100       458 $decimal = substr($number, length($integer)+1)
620             if (length($integer) < length($number));
621 95 100       146 $decimal = '' unless defined $decimal;
622              
623             # Add trailing 0's if $trailing_zeroes is set.
624 95 100 100     310 $decimal .= '0'x( $precision - length($decimal) )
625             if $trailing_zeroes && $precision > length($decimal);
626              
627             # Add the commas (or whatever is in thousands_sep). If
628             # thousands_sep is the empty string, do nothing.
629 95 50       193 if ($thousands_sep)
630             {
631             # Add leading 0's so length($integer) is divisible by 3
632 95         220 $integer = '0'x(3 - (length($integer) % 3)).$integer;
633              
634             # Split $integer into groups of 3 characters and insert commas
635             $integer = join($thousands_sep,
636 95         433 grep {$_ ne ''} split(/(...)/, $integer));
  260         527  
637              
638             # Strip off leading zeroes and optional thousands separator
639 95         867 $integer =~ s/^0+(?:\Q$thousands_sep\E)?//;
640             }
641 95 100       204 $integer = '0' if $integer eq '';
642              
643             # Combine integer and decimal parts and return the result.
644 95 100 66     320 my $result = ((defined $decimal && length $decimal) ?
645             join($decimal_point, $integer, $decimal) :
646             $integer);
647              
648 95 100       467 return ($sign < 0) ? $self->format_negative($result) : $result;
649             }
650              
651             ##----------------------------------------------------------------------
652              
653             #pod =method format_negative
654             #pod
655             #pod my $str = $formatter->($number, $picture);
656             #pod
657             #pod Formats a negative number. Picture should be a string that contains
658             #pod the letter C where the number should be inserted. For example, for
659             #pod standard negative numbers you might use ``C<-x>'', while for
660             #pod accounting purposes you might use ``C<(x)>''. If the specified number
661             #pod begins with a ``-'' character, that will be removed before formatting,
662             #pod but formatting will occur whether or not the number is negative.
663             #pod
664             #pod =cut
665              
666             sub format_negative
667             {
668 8     8 1 32 my($self, $number, $format) = _get_self @_;
669              
670 8 100       27 unless (defined($number))
671             {
672 1         5 _complain_undef();
673 1         11 $number = 0;
674             }
675              
676 8 50       19 $format = $self->{neg_format} unless defined $format;
677 8 50       24 croak "Letter x must be present in picture in format_negative()"
678             unless $format =~ /x/;
679 8         25 $number =~ s/^-//;
680 8         21 $format =~ s/x/$number/;
681 8         39 return $format;
682             }
683              
684             ##----------------------------------------------------------------------
685              
686             #pod =method format_picture
687             #pod
688             #pod my $str = $formatter->format_picture($number, $picture);
689             #pod
690             #pod Returns a string based on C<$picture> with the C<#> characters
691             #pod replaced by digits from C<$number>. If the length of the integer part
692             #pod of $number is too large to fit, the C<#> characters are replaced with
693             #pod asterisks (C<*>) instead. Examples:
694             #pod
695             #pod format_picture(100.023, 'USD ##,###.##') yields 'USD 100.02'
696             #pod format_picture(1000.23, 'USD ##,###.##') yields 'USD 1,000.23'
697             #pod format_picture(10002.3, 'USD ##,###.##') yields 'USD 10,002.30'
698             #pod format_picture(100023, 'USD ##,###.##') yields 'USD **,***.**'
699             #pod format_picture(1.00023, 'USD #.###,###') yields 'USD 1.002,300'
700             #pod
701             #pod The comma (,) and period (.) you see in the picture examples should
702             #pod match the values of C and C,
703             #pod respectively, for proper operation. However, the C
704             #pod characters in C<$picture> need not occur every three digits; the
705             #pod I use of that variable by this function is to remove leading
706             #pod commas (see the first example above). There may not be more than one
707             #pod instance of C in C<$picture>.
708             #pod
709             #pod The value of C is used to determine how negative numbers
710             #pod are displayed. The result of this is that the output of this function
711             #pod my have unexpected spaces before and/or after the number. This is
712             #pod necessary so that positive and negative numbers are formatted into a
713             #pod space the same size. If you are only using positive numbers and want
714             #pod to avoid this problem, set NEG_FORMAT to "x".
715             #pod
716             #pod =cut
717              
718             sub format_picture
719             {
720 13     13 1 15022 my ($self, $number, $picture) = _get_self @_;
721              
722 13 100       33 unless (defined($number))
723             {
724 1         5 _complain_undef();
725 1         9 $number = 0;
726             }
727              
728 13 50       25 croak "Picture not defined" unless defined($picture);
729              
730 13         33 $self->_check_seps();
731              
732             # Handle negative numbers
733 13         79 my($neg_prefix) = $self->{neg_format} =~ /^([^x]+)/;
734 13         33 my($pic_prefix) = $picture =~ /^([^\#]+)/;
735 13         21 my $neg_pic = $self->{neg_format};
736 13         63 (my $pos_pic = $self->{neg_format}) =~ s/[^x\s]/ /g;
737 13         36 (my $pos_prefix = $neg_prefix) =~ s/[^x\s]/ /g;
738 13         37 $neg_pic =~ s/x/$picture/;
739 13         25 $pos_pic =~ s/x/$picture/;
740 13         27 my $sign = $number <=> 0;
741 13 100       37 $number = abs($number) if $sign < 0;
742 13 100       24 $picture = $sign < 0 ? $neg_pic : $pos_pic;
743 13 100       26 my $sign_prefix = $sign < 0 ? $neg_prefix : $pos_prefix;
744              
745             # Split up the picture and die if there is more than one $DECIMAL_POINT
746 13         84 my($pic_int, $pic_dec, @cruft) =
747             split(/\Q$self->{decimal_point}\E/, $picture);
748 13 50       26 $pic_int = '' unless defined $pic_int;
749 13 100       21 $pic_dec = '' unless defined $pic_dec;
750              
751 13 50       21 croak "Only one decimal separator permitted in picture"
752             if @cruft;
753              
754             # Obtain precision from the length of the decimal part...
755 13         22 my $precision = $pic_dec; # start with copying it
756 13         26 $precision =~ s/[^\#]//g; # eliminate all non-# characters
757 13         18 $precision = length $precision; # take the length of the result
758              
759             # Format the number
760 13         42 $number = $self->round($number, $precision);
761              
762             # Obtain the length of the integer portion just like we did for $precision
763 13         20 my $intsize = $pic_int; # start with copying it
764 13         69 $intsize =~ s/[^\#]//g; # eliminate all non-# characters
765 13         23 $intsize = length $intsize; # take the length of the result
766              
767             # Split up $number same as we did for $picture earlier
768 13         94 my($num_int, $num_dec) = split(/\./, $number, 2);
769 13 50       29 $num_int = '' unless defined $num_int;
770 13 100       29 $num_dec = '' unless defined $num_dec;
771              
772             # Check if the integer part will fit in the picture
773 13 100       26 if (length $num_int > $intsize)
774             {
775 2         10 $picture =~ s/\#/\*/g; # convert # to * and return it
776 2 50       4 $pic_prefix = "" unless defined $pic_prefix;
777 2         74 $picture =~ s/^(\Q$sign_prefix\E)(\Q$pic_prefix\E)(\s*)/$2$3$1/;
778 2         13 return $picture;
779             }
780              
781             # Split each portion of number and picture into arrays of characters
782 11         28 my @num_int = split(//, $num_int);
783 11         21 my @num_dec = split(//, $num_dec);
784 11         36 my @pic_int = split(//, $pic_int);
785 11         18 my @pic_dec = split(//, $pic_dec);
786              
787             # Now we copy those characters into @result.
788 11         15 my @result;
789             @result = ($self->{decimal_point})
790 11 100       86 if $picture =~ /\Q$self->{decimal_point}\E/;
791             # For each characture in the decimal part of the picture, replace '#'
792             # signs with digits from the number.
793 11         16 my $char;
794 11         51 foreach $char (@pic_dec)
795             {
796 18 100 100     57 $char = (shift(@num_dec) || 0) if ($char eq '#');
797 18         33 push (@result, $char);
798             }
799              
800             # For each character in the integer part of the picture (moving right
801             # to left this time), replace '#' signs with digits from the number,
802             # or spaces if we've run out of numbers.
803 11         28 while ($char = pop @pic_int)
804             {
805 121 100       253 $char = pop(@num_int) if ($char eq '#');
806             $char = ' ' if (!defined($char) ||
807 121 100 100     360 $char eq $self->{thousands_sep} && $#num_int < 0);
      100        
808 121         285 unshift (@result, $char);
809             }
810              
811             # Combine @result into a string and return it.
812 11         38 my $result = join('', @result);
813 11 50       21 $sign_prefix = '' unless defined $sign_prefix;
814 11 100       23 $pic_prefix = '' unless defined $pic_prefix;
815 11         413 $result =~ s/^(\Q$sign_prefix\E)(\Q$pic_prefix\E)(\s*)/$2$3$1/;
816 11         108 $result;
817             }
818              
819             ##----------------------------------------------------------------------
820              
821             #pod =method format_price
822             #pod
823             #pod my $str = $formatter->format_price($number, $precision, $symbol);
824             #pod
825             #pod Returns a string containing C<$number> formatted similarly to
826             #pod C, except that the decimal portion may have trailing
827             #pod zeroes added to make it be exactly C<$precision> characters long, and
828             #pod the currency string will be prefixed.
829             #pod
830             #pod The C<$symbol> attribute may be one of "INT_CURR_SYMBOL" or
831             #pod "CURRENCY_SYMBOL" (case insensitive) to use the value of that
832             #pod attribute of the object, or a string containing the symbol to be used.
833             #pod The default is "INT_CURR_SYMBOL" if this argument is undefined or not
834             #pod given; if set to the empty string, or if set to undef and the
835             #pod C attribute of the object is the empty string, no
836             #pod currency will be added.
837             #pod
838             #pod If C<$precision> is not provided, the default of 2 will be used.
839             #pod Examples:
840             #pod
841             #pod format_price(12.95) yields 'USD 12.95'
842             #pod format_price(12) yields 'USD 12.00'
843             #pod format_price(12, 3) yields '12.000'
844             #pod
845             #pod The third example assumes that C is the empty string.
846             #pod
847             #pod =cut
848              
849             sub format_price
850             {
851 55     55 1 19619 my ($self, $number, $precision, $curr_symbol) = _get_self @_;
852              
853 55 100       98 unless (defined($number))
854             {
855 1         3 _complain_undef();
856 1         6 $number = 0;
857             }
858              
859             # Determine what the monetary symbol should be
860             $curr_symbol = $self->{int_curr_symbol}
861 55 100 66     181 if (!defined($curr_symbol) || lc($curr_symbol) eq "int_curr_symbol");
862             $curr_symbol = $self->{currency_symbol}
863 55 100 66     195 if (!defined($curr_symbol) || lc($curr_symbol) eq "currency_symbol");
864 55 50       85 $curr_symbol = "" unless defined($curr_symbol);
865              
866             # Determine which value to use for frac digits
867             my $frac_digits = ($curr_symbol eq $self->{int_curr_symbol} ?
868 55 100       115 $self->{int_frac_digits} : $self->{frac_digits});
869              
870             # Determine precision for decimal portion
871 55 100       78 $precision = $frac_digits unless defined $precision;
872 55 50       72 $precision = $self->{decimal_digits} unless defined $precision; # fallback
873 55 50       82 $precision = 2 unless defined $precision; # default
874              
875             # Determine sign and absolute value
876 55         98 my $sign = $number <=> 0;
877 55 100       93 $number = abs($number) if $sign < 0;
878              
879             # format it first
880 55         108 $number = $self->format_number($number, $precision, undef, 1);
881              
882             # Now we make sure the decimal part has enough zeroes
883 55         267 my ($integer, $decimal) =
884             split(/\Q$self->{mon_decimal_point}\E/, $number, 2);
885 55 100       90 $decimal = '0'x$precision unless $decimal;
886 55         79 $decimal .= '0'x($precision - length $decimal);
887              
888             # Extract positive or negative values
889 55         65 my($sep_by_space, $cs_precedes, $sign_posn, $sign_symbol);
890 55 100       71 if ($sign < 0)
891             {
892 41         64 $sep_by_space = $self->{n_sep_by_space};
893 41         48 $cs_precedes = $self->{n_cs_precedes};
894 41         46 $sign_posn = $self->{n_sign_posn};
895 41         50 $sign_symbol = $self->{negative_sign};
896             }
897             else
898             {
899 14         21 $sep_by_space = $self->{p_sep_by_space};
900 14         15 $cs_precedes = $self->{p_cs_precedes};
901 14         17 $sign_posn = $self->{p_sign_posn};
902 14         19 $sign_symbol = $self->{positive_sign};
903             }
904              
905             # Combine it all back together.
906             my $result = ($precision ?
907 55 100       121 join($self->{mon_decimal_point}, $integer, $decimal) :
908             $integer);
909              
910             # Determine where spaces go, if any
911 55         64 my($sign_sep, $curr_sep);
912 55 100       87 if ($sep_by_space == 0)
    100          
    50          
913             {
914 20         47 $sign_sep = $curr_sep = "";
915             }
916             elsif ($sep_by_space == 1)
917             {
918 23         51 $sign_sep = "";
919 23         26 $curr_sep = " ";
920             }
921             elsif ($sep_by_space == 2)
922             {
923 12         13 $sign_sep = " ";
924 12         11 $curr_sep = "";
925             }
926             else
927             {
928 0         0 croak "Invalid sep_by_space value";
929             }
930              
931             # Add sign, if any
932 55 100 66     168 if ($sign_posn >= 0 && $sign_posn <= 2)
    50 66        
933             {
934             # Combine with currency symbol and return
935 35 50       54 if ($curr_symbol ne "")
936             {
937 35 100       44 if ($cs_precedes)
938             {
939 26         45 $result = $curr_symbol.$curr_sep.$result;
940             }
941             else
942             {
943 9         14 $result = $result.$curr_sep.$curr_symbol;
944             }
945             }
946              
947 35 100       60 if ($sign_posn == 0)
    100          
948             {
949 7         36 return "($result)";
950             }
951             elsif ($sign_posn == 1)
952             {
953 21         114 return $sign_symbol.$sign_sep.$result;
954             }
955             else # $sign_posn == 2
956             {
957 7         34 return $result.$sign_sep.$sign_symbol;
958             }
959             }
960              
961             elsif ($sign_posn == 3 || $sign_posn == 4)
962             {
963 20 100       33 if ($sign_posn == 3)
964             {
965 13         22 $curr_symbol = $sign_symbol.$sign_sep.$curr_symbol;
966             }
967             else # $sign_posn == 4
968             {
969 7         9 $curr_symbol = $curr_symbol.$sign_sep.$sign_symbol;
970             }
971              
972             # Combine with currency symbol and return
973 20 100       26 if ($cs_precedes)
974             {
975 11         48 return $curr_symbol.$curr_sep.$result;
976             }
977             else
978             {
979 9         57 return $result.$curr_sep.$curr_symbol;
980             }
981             }
982              
983             else
984             {
985 0         0 croak "Invalid *_sign_posn value";
986             }
987             }
988              
989             ##----------------------------------------------------------------------
990              
991             #pod =method format_bytes
992             #pod
993             #pod my $str = $formatter->format_bytes($number, %options);
994             #pod
995             #pod my $str = $formatter->format_bytes($number, $precision); # deprecated
996             #pod
997             #pod Returns a string containing C<$number> formatted similarly to
998             #pod C, except that large numbers may be abbreviated by
999             #pod adding a suffix to indicate 1024, 1,048,576, or 1,073,741,824 bytes.
1000             #pod Suffix may be the traditional K, M, or G (default); or the IEC
1001             #pod standard 60027 "KiB," "MiB," or "GiB" depending on the "mode" option.
1002             #pod
1003             #pod Negative values will result in an error.
1004             #pod
1005             #pod The second parameter can be either a hash that sets options, or a
1006             #pod number. Using a number here is deprecated and will generate a
1007             #pod warning; early versions of Number::Format only allowed a numeric
1008             #pod value. A future release of Number::Format will change this warning to
1009             #pod an error. New code should use a hash instead to set options. If it
1010             #pod is a number this sets the value of the "precision" option.
1011             #pod
1012             #pod Valid options are:
1013             #pod
1014             #pod =over 4
1015             #pod
1016             #pod =item precision
1017             #pod
1018             #pod Set the precision for displaying numbers. If not provided, a default
1019             #pod of 2 will be used. Examples:
1020             #pod
1021             #pod format_bytes(12.95) yields '12.95'
1022             #pod format_bytes(12.95, precision => 0) yields '13'
1023             #pod format_bytes(2048) yields '2K'
1024             #pod format_bytes(2048, mode => "iec") yields '2KiB'
1025             #pod format_bytes(9999999) yields '9.54M'
1026             #pod format_bytes(9999999, precision => 1) yields '9.5M'
1027             #pod
1028             #pod =item unit
1029             #pod
1030             #pod Sets the default units used for the results. The default is to
1031             #pod determine this automatically in order to minimize the length of the
1032             #pod string. In other words, numbers greater than or equal to 1024 (or
1033             #pod other number given by the 'base' option, q.v.) will be divided by 1024
1034             #pod and C<$KILO_SUFFIX> or C<$KIBI_SUFFIX> added; if greater than or equal
1035             #pod to 1048576 (1024*1024), it will be divided by 1048576 and
1036             #pod C<$MEGA_SUFFIX> or C<$MEBI_SUFFIX> appended to the end; etc.
1037             #pod
1038             #pod However if a value is given for C it will use that value
1039             #pod instead. The first letter (case-insensitive) of the value given
1040             #pod indicates the threshhold for conversion; acceptable values are T (for
1041             #pod tera/tebi), G (for giga/gibi), M (for mega/mebi), K (for kilo/kibi), or
1042             #pod A (for automatic, the default). For example:
1043             #pod
1044             #pod format_bytes(1048576, unit => 'K') yields '1,024K'
1045             #pod instead of '1M'
1046             #pod
1047             #pod Note that the valid values to this option do not vary even when the
1048             #pod suffix configuration variables have been changed.
1049             #pod
1050             #pod =item base
1051             #pod
1052             #pod Sets the number at which the C<$KILO_SUFFIX> is added. Default is
1053             #pod 1024. Set to any value; the only other useful value is probably 1000,
1054             #pod as hard disk manufacturers use that number to make their disks sound
1055             #pod bigger than they really are.
1056             #pod
1057             #pod If the mode (see below) is set to "iec" or "iec60027" then setting the
1058             #pod base option results in an error.
1059             #pod
1060             #pod =item mode
1061             #pod
1062             #pod Traditionally, bytes have been given in SI (metric) units such as
1063             #pod "kilo" and "mega" even though they represent powers of 2 (1024, etc.)
1064             #pod rather than powers of 10 (1000, etc.) This "binary prefix" causes
1065             #pod much confusion in consumer products where "GB" may mean either
1066             #pod 1,048,576 or 1,000,000, for example. The International
1067             #pod Electrotechnical Commission has created standard IEC 60027 to
1068             #pod introduce prefixes Ki, Mi, Gi, etc. ("kibibytes," "mebibytes,"
1069             #pod "gibibytes," etc.) to remove this confusion. Specify a mode option
1070             #pod with either "traditional" or "iec60027" (or abbreviate as "trad" or
1071             #pod "iec") to indicate which type of binary prefix you want format_bytes
1072             #pod to use. For backward compatibility, "traditional" is the default.
1073             #pod See http://en.wikipedia.org/wiki/Binary_prefix for more information.
1074             #pod
1075             #pod =back
1076             #pod
1077             #pod =cut
1078              
1079             sub format_bytes
1080             {
1081 22     22 1 368586 my ($self, $number, @options) = _get_self @_;
1082              
1083 22 100       48 unless (defined($number))
1084             {
1085 1         6 _complain_undef();
1086 1         10 $number = 0;
1087             }
1088              
1089 22 50       38 croak "Negative number not allowed in format_bytes"
1090             if $number < 0;
1091              
1092             # If a single scalar is given instead of key/value pairs for
1093             # @options, treat that as the value of the precision option.
1094 22         29 my %options;
1095 22 50       41 if (@options == 1)
1096             {
1097             # To be changed to 'croak' in a future release:
1098 0         0 carp "format_bytes: number instead of options is deprecated";
1099 0         0 %options = ( precision => $options[0] );
1100             }
1101             else
1102             {
1103 22         53 %options = @options;
1104             }
1105              
1106             # Set default for precision. Test using defined because it may be 0.
1107             $options{precision} = $self->{decimal_digits}
1108 22 100       62 unless defined $options{precision};
1109             $options{precision} = 2
1110 22 50       35 unless defined $options{precision}; # default
1111              
1112 22   100     62 $options{mode} ||= "traditional";
1113 22         27 my($ksuff, $msuff, $gsuff, $tsuff);
1114 22 100       137 if ($options{mode} =~ /^iec(60027)?$/i)
    50          
1115             {
1116             ($ksuff, $msuff, $gsuff, $tsuff) =
1117 8         20 @$self{qw(kibi_suffix mebi_suffix gibi_suffix tebi_suffix)};
1118             croak "base option not allowed in iec60027 mode"
1119 8 50       16 if exists $options{base};
1120             }
1121             elsif ($options{mode} =~ /^trad(itional)?$/i)
1122             {
1123             ($ksuff, $msuff, $gsuff, $tsuff) =
1124 14         48 @$self{qw(kilo_suffix mega_suffix giga_suffix tera_suffix)};
1125             }
1126             else
1127             {
1128 0         0 croak "Invalid mode";
1129             }
1130              
1131             # Set default for "base" option. Calculate threshold values for
1132             # kilo, mega, giga, and tera values. Useful values of "base" are 1024 or
1133             # 1000, but any number can be used. Larger numbers may cause overflows at
1134             # some threshholds, of course.
1135 22         56 my %mult = _get_multipliers($options{base});
1136              
1137             # Process "unit" option. Set default, then take first character
1138             # and convert to upper case.
1139             $options{unit} = "auto"
1140 22 100       59 unless defined $options{unit};
1141 22         50 my $unit = uc(substr($options{unit},0,1));
1142              
1143             # Process "auto" first (default). Based on size of number,
1144             # automatically determine which unit to use.
1145 22 100       44 if ($unit eq 'A')
1146             {
1147 19 100       59 if ($number >= $mult{tera})
    100          
    100          
    100          
1148             {
1149 3         5 $unit = 'T';
1150             }
1151             elsif ($number >= $mult{giga})
1152             {
1153 2         3 $unit = 'G';
1154             }
1155             elsif ($number >= $mult{mega})
1156             {
1157 6         11 $unit = 'M';
1158             }
1159             elsif ($number >= $mult{kilo})
1160             {
1161 3         5 $unit = 'K';
1162             }
1163             else
1164             {
1165 5         5 $unit = 'N';
1166             }
1167             }
1168              
1169             # Based on unit, whether specified or determined above, divide the
1170             # number and determine what suffix to use.
1171 22         27 my $suffix = "";
1172 22 100       52 if ($unit eq 'T')
    100          
    100          
    100          
    50          
1173             {
1174 4         7 $number /= $mult{tera};
1175 4         6 $suffix = $tsuff;
1176             }
1177             elsif ($unit eq 'G')
1178             {
1179 2         4 $number /= $mult{giga};
1180 2         4 $suffix = $gsuff;
1181             }
1182             elsif ($unit eq 'M')
1183             {
1184 6         9 $number /= $mult{mega};
1185 6         9 $suffix = $msuff;
1186             }
1187             elsif ($unit eq 'K')
1188             {
1189 5         9 $number /= $mult{kilo};
1190 5         6 $suffix = $ksuff;
1191             }
1192             elsif ($unit ne 'N')
1193             {
1194 0         0 croak "Invalid unit option";
1195             }
1196              
1197             # Format the number and add the suffix.
1198 22         51 return $self->format_number($number, $options{precision}) . $suffix;
1199             }
1200              
1201             ##----------------------------------------------------------------------
1202              
1203             #pod =method unformat_number
1204             #pod
1205             #pod my $str = $formatter->format_number($formatted);
1206             #pod
1207             #pod Converts a string as returned by C,
1208             #pod C, or C, and returns the
1209             #pod corresponding value as a numeric scalar. Returns C if the
1210             #pod number does not contain any digits. Examples:
1211             #pod
1212             #pod unformat_number('USD 12.95') yields 12.95
1213             #pod unformat_number('USD 12.00') yields 12
1214             #pod unformat_number('foobar') yields undef
1215             #pod unformat_number('1234-567@.8') yields 1234567.8
1216             #pod
1217             #pod The value of C is used to determine where to separate
1218             #pod the integer and decimal portions of the input. All other non-digit
1219             #pod characters, including but not limited to C and
1220             #pod C, are removed.
1221             #pod
1222             #pod If the number matches the pattern of C I there is a C<->
1223             #pod character before any of the digits, then a negative number is returned.
1224             #pod
1225             #pod If the number ends with the C, C,
1226             #pod C, C, C, C,
1227             #pod C, or C characters, then the number returned
1228             #pod will be multiplied by the appropriate multiple of 1024 (or if the base
1229             #pod option is given, by the multiple of that value) as appropriate. Examples:
1230             #pod
1231             #pod unformat_number("4K", base => 1024) yields 4096
1232             #pod unformat_number("4K", base => 1000) yields 4000
1233             #pod unformat_number("4KiB", base => 1024) yields 4096
1234             #pod unformat_number("4G") yields 4294967296
1235             #pod
1236             #pod =cut
1237              
1238             sub unformat_number
1239             {
1240 23     23 1 435291 my ($self, $formatted, %options) = _get_self @_;
1241              
1242 23 100       71 unless (defined($formatted))
1243             {
1244 1         5 _complain_undef();
1245 1         11 $formatted = "";
1246             }
1247              
1248 23         72 $self->_check_seps();
1249 23 100       102 return undef unless $formatted =~ /\d/; # require at least one digit
1250              
1251             # Regular expression for detecting decimal point
1252 21         183 my $pt = qr/\Q$self->{decimal_point}\E/;
1253              
1254             # ru_RU locale has comma for decimal_point, but period for
1255             # mon_decimal_point! But as long as thousands_sep is different
1256             # from either, we can allow either decimal point.
1257 21 0 33     184 if ($self->{mon_decimal_point} &&
      33        
      33        
1258             $self->{decimal_point} ne $self->{mon_decimal_point} &&
1259             $self->{decimal_point} ne $self->{mon_thousands_sep} &&
1260             $self->{mon_decimal_point} ne $self->{thousands_sep})
1261             {
1262 0         0 $pt = qr/(?:\Q$self->{decimal_point}\E|
1263             \Q$self->{mon_decimal_point}\E)/x;
1264             }
1265              
1266             # Detect if it ends with one of the kilo / mega / giga / tera suffixes.
1267 21         335 my $kp = ($formatted =~
1268             s/\s*($self->{kilo_suffix}|$self->{kibi_suffix})\s*$//);
1269 21         244 my $mp = ($formatted =~
1270             s/\s*($self->{mega_suffix}|$self->{mebi_suffix})\s*$//);
1271 21         241 my $gp = ($formatted =~
1272             s/\s*($self->{giga_suffix}|$self->{gibi_suffix})\s*$//);
1273 21         201 my $tp = ($formatted =~
1274             s/\s*($self->{tera_suffix}|$self->{tebi_suffix})\s*$//);
1275 21         118 my %mult = _get_multipliers($options{base});
1276              
1277             # Split number into integer and decimal parts
1278 17         114 my ($integer, $decimal, @cruft) = split($pt, $formatted);
1279 17 50       48 croak "Only one decimal separator permitted"
1280             if @cruft;
1281              
1282             # It's negative if the first non-digit character is a -
1283 17 100       58 my $sign = $formatted =~ /^\D*-/ ? -1 : 1;
1284 17         64 my($before_re, $after_re) = split /x/, $self->{neg_format}, 2;
1285 17 100       218 $sign = -1 if $formatted =~ /\Q$before_re\E(.+)\Q$after_re\E/;
1286              
1287             # Strip out all non-digits from integer and decimal parts
1288 17 50       45 $integer = '' unless defined $integer;
1289 17 100       48 $decimal = '' unless defined $decimal;
1290 17         61 $integer =~ s/\D//g;
1291 17         38 $decimal =~ s/\D//g;
1292              
1293             # Join back up, using period, and add 0 to make Perl think it's a number
1294 17         102 my $number = join('.', $integer, $decimal) + 0;
1295 17 100       41 $number = -$number if $sign < 0;
1296              
1297             # Scale the number if it ended in kilo or mega suffix.
1298 17 100       46 $number *= $mult{kilo} if $kp;
1299 17 100       41 $number *= $mult{mega} if $mp;
1300 17 100       44 $number *= $mult{giga} if $gp;
1301 17 100       43 $number *= $mult{tera} if $tp;
1302              
1303 17         166 return $number;
1304             }
1305              
1306             ###---------------------------------------------------------------------
1307              
1308             #pod =head1 CAVEATS
1309             #pod
1310             #pod Some systems, notably OpenBSD, may have incomplete locale support.
1311             #pod Using this module together with L in OpenBSD may therefore
1312             #pod not produce the intended results.
1313             #pod
1314             #pod This library takes some pain to cope with numeric precision, but it doesn't
1315             #pod solve every problem. Working with terabyte sizes on a 32-bit perl may have
1316             #pod imprecise results.
1317             #pod
1318             #pod =cut
1319              
1320             1;
1321              
1322             __END__