File Coverage

blib/lib/Lingua/RON/Num2Word.pm
Criterion Covered Total %
statement 29 65 44.6
branch 2 44 4.5
condition 4 45 8.8
subroutine 9 11 81.8
pod 3 3 100.0
total 47 168 27.9


line stmt bran cond sub pod time code
1             # For Emacs: -*- mode:cperl; eval: (folding-mode 1); coding:utf-8 -*-
2              
3             package Lingua::RON::Num2Word;
4             # ABSTRACT: Number to word conversion in Romanian
5              
6 1     1   133689 use 5.16.0;
  1         3  
7 1     1   4 use utf8;
  1         2  
  1         10  
8 1     1   21 use warnings;
  1         1  
  1         64  
9              
10             # {{{ use block
11              
12 1     1   7 use Carp;
  1         45  
  1         94  
13 1     1   533 use Export::Attrs;
  1         10593  
  1         8  
14 1     1   962 use Readonly;
  1         5683  
  1         772  
15              
16             # }}}
17             # {{{ variable declarations
18              
19             my Readonly::Scalar $COPY = 'Copyright (c) PetaMem, s.r.o. 2002-present';
20             our $VERSION = '0.2603300';
21              
22             # }}}
23              
24             # {{{ num2ron_cardinal convert number to text
25              
26             sub num2ron_cardinal :Export {
27 2     2 1 245593 my $positive = shift;
28              
29 2 50 33     41 croak 'You should specify a number from interval [0, 999_999_999]'
      33        
      33        
30             if !defined $positive
31             || $positive !~ m{\A\d+\z}xms
32             || $positive < 0
33             || $positive > 999_999_999;
34              
35 2         14 my @units = ('zero', 'unu', 'doi', 'trei', 'patru', 'cinci',
36             'șase', 'șapte', 'opt', 'nouă');
37              
38 2         12 my @teens = ('zece', 'unsprezece', 'doisprezece', 'treisprezece',
39             'paisprezece', 'cincisprezece', 'șaisprezece',
40             'șaptesprezece', 'optsprezece', 'nouăsprezece');
41              
42 2         9 my @tens = ('', '', 'douăzeci', 'treizeci', 'patruzeci', 'cincizeci',
43             'șaizeci', 'șaptezeci', 'optzeci', 'nouăzeci');
44              
45 2 50 33     19 return $units[$positive] if ($positive >= 0 && $positive < 10);
46 0 0 0       return $teens[$positive - 10] if ($positive >= 10 && $positive < 20);
47              
48 0           my $out;
49             my $remain;
50              
51 0 0 0       if ($positive > 19 && $positive < 100) { # 20 .. 99
    0 0        
    0 0        
    0 0        
    0 0        
    0 0        
    0 0        
    0          
52 0           my $ten_idx = int($positive / 10);
53 0           $remain = $positive % 10;
54              
55 0           $out = $tens[$ten_idx];
56 0 0         $out .= ' și ' . $units[$remain] if ($remain);
57             }
58             elsif ($positive == 100) { # 100
59 0           $out = 'o sută';
60             }
61             elsif ($positive > 100 && $positive < 200) { # 101 .. 199
62 0           $remain = $positive % 100;
63 0           $out = 'o sută ' . num2ron_cardinal($remain);
64             }
65             elsif ($positive >= 200 && $positive < 1000) { # 200 .. 999
66 0           my $hun_idx = int($positive / 100);
67 0           $remain = $positive % 100;
68              
69 0 0         $out = $hun_idx == 2
70             ? 'două sute'
71             : num2ron_cardinal($hun_idx) . ' sute';
72 0 0         $out .= ' ' . num2ron_cardinal($remain) if ($remain);
73             }
74             elsif ($positive >= 1000 && $positive < 2000) { # 1000 .. 1999
75 0           $remain = $positive % 1000;
76              
77 0           $out = 'o mie';
78 0 0         $out .= ' ' . num2ron_cardinal($remain) if ($remain);
79             }
80             elsif ($positive >= 2000 && $positive < 1_000_000) { # 2000 .. 999_999
81 0           my $tho_idx = int($positive / 1000);
82 0           $remain = $positive % 1000;
83              
84 0 0         $out = $tho_idx == 2
85             ? 'două mii'
86             : num2ron_cardinal($tho_idx) . ' mii';
87 0 0         $out .= ' ' . num2ron_cardinal($remain) if ($remain);
88             }
89             elsif ($positive >= 1_000_000 && $positive < 2_000_000) { # 1_000_000 .. 1_999_999
90 0           $remain = $positive % 1_000_000;
91              
92 0           $out = 'un milion';
93 0 0         $out .= ' ' . num2ron_cardinal($remain) if ($remain);
94             }
95             elsif ($positive >= 2_000_000 && $positive < 1_000_000_000) { # 2_000_000 .. 999_999_999
96 0           my $mil_idx = int($positive / 1_000_000);
97 0           $remain = $positive % 1_000_000;
98              
99 0 0         $out = $mil_idx == 2
100             ? 'două milioane'
101             : num2ron_cardinal($mil_idx) . ' milioane';
102 0 0         $out .= ' ' . num2ron_cardinal($remain) if ($remain);
103             }
104              
105 0           return $out;
106 1     1   12 }
  1         3  
  1         10  
107              
108             # }}}
109              
110              
111             # {{{ num2ron_ordinal convert number to ordinal text
112              
113             sub num2ron_ordinal :Export {
114 0     0 1   my $number = shift;
115              
116 0 0 0       croak 'You should specify a number from interval [1, 999_999_999]'
      0        
      0        
117             if !defined $number
118             || $number !~ m{\A\d+\z}xms
119             || $number < 1
120             || $number > 999_999_999;
121              
122             # Irregular ordinals 1-10
123 0           my %irregular = (
124             1 => 'primul',
125             2 => 'al doilea',
126             3 => 'al treilea',
127             4 => 'al patrulea',
128             5 => 'al cincilea',
129             6 => 'al șaselea',
130             7 => 'al șaptelea',
131             8 => 'al optulea',
132             9 => 'al nouălea',
133             10 => 'al zecelea',
134             );
135              
136 0 0         return $irregular{$number} if exists $irregular{$number};
137              
138             # For 11+, form: "al" + cardinal + "lea"
139 0           my $cardinal = num2ron_cardinal($number);
140              
141 0           return 'al ' . $cardinal . 'lea';
142 1     1   622 }
  1         2  
  1         6  
143              
144             # }}}
145              
146             # {{{ capabilities declare supported features
147              
148             sub capabilities {
149             return {
150 0     0 1   cardinal => 1,
151             ordinal => 1,
152             };
153             }
154              
155             # }}}
156             1;
157              
158             __END__