| Filename | /Users/timbo/perl5/perlbrew/perls/perl-5.18.2/lib/site_perl/5.18.2/Lingua/EN/Inflect.pm |
| Statements | Executed 119135 statements in 673ms |
| Calls | P | F | Exclusive Time |
Inclusive Time |
Subroutine |
|---|---|---|---|---|---|
| 75807 | 63 | 1 | 341ms | 341ms | Lingua::EN::Inflect::CORE:match (opcode) |
| 1179 | 1 | 1 | 172ms | 511ms | Lingua::EN::Inflect::_PL_noun |
| 1220 | 1 | 1 | 69.5ms | 98.4ms | Lingua::EN::Inflect::_PL_special_verb |
| 34192 | 32 | 1 | 34.1ms | 34.1ms | Lingua::EN::Inflect::CORE:regcomp (opcode) |
| 1220 | 1 | 1 | 21.0ms | 30.3ms | Lingua::EN::Inflect::_PL_special_adjective |
| 1220 | 1 | 1 | 18.7ms | 675ms | Lingua::EN::Inflect::PL |
| 1220 | 1 | 1 | 10.8ms | 13.0ms | Lingua::EN::Inflect::postprocess |
| 3619 | 3 | 1 | 6.66ms | 6.66ms | Lingua::EN::Inflect::ud_match |
| 1 | 1 | 1 | 1.41ms | 9.79ms | Lingua::EN::Inflect::BEGIN@5 |
| 1233 | 3 | 1 | 590µs | 590µs | Lingua::EN::Inflect::CORE:subst (opcode) |
| 49 | 46 | 1 | 59µs | 59µs | Lingua::EN::Inflect::enclose |
| 1 | 1 | 1 | 11µs | 22µs | Lingua::EN::Inflect::BEGIN@3 |
| 1 | 1 | 1 | 10µs | 10µs | Lingua::EN::Inflect::CORE:sort (opcode) |
| 1 | 1 | 1 | 7µs | 55µs | Lingua::EN::Inflect::BEGIN@4 |
| 1 | 1 | 1 | 6µs | 6µs | Lingua::EN::Inflect::CORE:fteread (opcode) |
| 1 | 1 | 1 | 2µs | 2µs | Lingua::EN::Inflect::CORE:qr (opcode) |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::A |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::AN |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::NO |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::NUM |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::NUMWORDS |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::ORD |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::PART_PRES |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::PL_ADJ |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::PL_ADJ_eq |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::PL_N |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::PL_N_eq |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::PL_V |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::PL_V_eq |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::PL_eq |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::WORDLIST |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::_PL_check_plurals_ADJ |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::_PL_check_plurals_N |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::_PL_eq |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::_PL_general_verb |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::_PL_reg_plurals |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::__ANON__[:773] |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::__ANON__[:785] |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::__ANON__[:846] |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::_commify |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::_indef_article |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::checkpat |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::checkpatsubs |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::classical |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::def_a |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::def_adj |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::def_an |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::def_noun |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::def_verb |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::enword |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::hund |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::inflect |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::mill |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::ten |
| 0 | 0 | 0 | 0s | 0s | Lingua::EN::Inflect::unit |
| Line | State ments |
Time on line |
Calls | Time in subs |
Code |
|---|---|---|---|---|---|
| 1 | package Lingua::EN::Inflect; | ||||
| 2 | |||||
| 3 | 2 | 22µs | 2 | 33µs | # spent 22µs (11+11) within Lingua::EN::Inflect::BEGIN@3 which was called:
# once (11µs+11µs) by Pod::Wordlist::BEGIN@4 at line 3 # spent 22µs making 1 call to Lingua::EN::Inflect::BEGIN@3
# spent 11µs making 1 call to strict::import |
| 4 | 2 | 18µs | 2 | 103µs | # spent 55µs (7+48) within Lingua::EN::Inflect::BEGIN@4 which was called:
# once (7µs+48µs) by Pod::Wordlist::BEGIN@4 at line 4 # spent 55µs making 1 call to Lingua::EN::Inflect::BEGIN@4
# spent 48µs making 1 call to vars::import |
| 5 | 2 | 9.17ms | 2 | 16.7ms | # spent 9.79ms (1.41+8.38) within Lingua::EN::Inflect::BEGIN@5 which was called:
# once (1.41ms+8.38ms) by Pod::Wordlist::BEGIN@4 at line 5 # spent 9.79ms making 1 call to Lingua::EN::Inflect::BEGIN@5
# spent 6.93ms making 1 call to Env::import |
| 6 | |||||
| 7 | 1 | 1µs | require Exporter; | ||
| 8 | 1 | 7µs | @ISA = qw(Exporter); | ||
| 9 | |||||
| 10 | 1 | 400ns | our $VERSION = '1.895'; | ||
| 11 | |||||
| 12 | 1 | 12µs | %EXPORT_TAGS = | ||
| 13 | ( | ||||
| 14 | ALL => [ qw( classical inflect | ||||
| 15 | PL PL_N PL_V PL_ADJ NO NUM A AN | ||||
| 16 | PL_eq PL_N_eq PL_V_eq PL_ADJ_eq | ||||
| 17 | PART_PRES | ||||
| 18 | ORD | ||||
| 19 | NUMWORDS | ||||
| 20 | WORDLIST | ||||
| 21 | def_noun def_verb def_adj def_a def_an )], | ||||
| 22 | |||||
| 23 | INFLECTIONS => [ qw( classical inflect | ||||
| 24 | PL PL_N PL_V PL_ADJ PL_eq | ||||
| 25 | NO NUM A AN PART_PRES )], | ||||
| 26 | |||||
| 27 | PLURALS => [ qw( classical inflect | ||||
| 28 | PL PL_N PL_V PL_ADJ NO NUM | ||||
| 29 | PL_eq PL_N_eq PL_V_eq PL_ADJ_eq )], | ||||
| 30 | |||||
| 31 | COMPARISONS => [ qw( classical | ||||
| 32 | PL_eq PL_N_eq PL_V_eq PL_ADJ_eq )], | ||||
| 33 | |||||
| 34 | ARTICLES => [ qw( classical inflect NUM A AN )], | ||||
| 35 | |||||
| 36 | NUMERICAL => [ qw( ORD NUMWORDS )], | ||||
| 37 | |||||
| 38 | USER_DEFINED => [ qw( def_noun def_verb def_adj def_a def_an )], | ||||
| 39 | ); | ||||
| 40 | |||||
| 41 | 1 | 3µs | 1 | 24µs | Exporter::export_ok_tags(qw( ALL )); # spent 24µs making 1 call to Exporter::export_ok_tags |
| 42 | |||||
| 43 | # SUPPORT CLASSICAL PLURALIZATIONS | ||||
| 44 | |||||
| 45 | 1 | 1µs | my %def_classical = ( | ||
| 46 | all => 0, | ||||
| 47 | zero => 0, | ||||
| 48 | herd => 0, | ||||
| 49 | names => 1, | ||||
| 50 | persons => 0, | ||||
| 51 | ancient => 0, | ||||
| 52 | ); | ||||
| 53 | |||||
| 54 | 1 | 800ns | my %all_classical = ( | ||
| 55 | all => 1, | ||||
| 56 | zero => 1, | ||||
| 57 | herd => 1, | ||||
| 58 | names => 1, | ||||
| 59 | persons => 1, | ||||
| 60 | ancient => 1, | ||||
| 61 | ); | ||||
| 62 | |||||
| 63 | 1 | 2µs | my %classical = %def_classical; | ||
| 64 | |||||
| 65 | 1 | 2µs | my $classical_mode = join '|', keys %all_classical; | ||
| 66 | 1 | 29µs | 2 | 20µs | $classical_mode = qr/^(?:$classical_mode)$/; # spent 18µs making 1 call to Lingua::EN::Inflect::CORE:regcomp
# spent 2µs making 1 call to Lingua::EN::Inflect::CORE:qr |
| 67 | |||||
| 68 | sub classical | ||||
| 69 | { | ||||
| 70 | if (!@_) { | ||||
| 71 | %classical = %all_classical; | ||||
| 72 | return; | ||||
| 73 | } | ||||
| 74 | if (@_==1 && $_[0] !~ $classical_mode) { | ||||
| 75 | %classical = $_[0] ? %all_classical : (); | ||||
| 76 | return; | ||||
| 77 | } | ||||
| 78 | while (@_) { | ||||
| 79 | my $arg = shift; | ||||
| 80 | if ($arg !~ $classical_mode) { | ||||
| 81 | die "Unknown classical mode ($arg)\n"; | ||||
| 82 | } | ||||
| 83 | if (@_ && $_[0] !~ $classical_mode) { $classical{$arg} = shift; } | ||||
| 84 | else { $classical{$arg} = 1; } | ||||
| 85 | |||||
| 86 | if ($arg eq 'all') { | ||||
| 87 | %classical = $classical{all} ? %all_classical : (); | ||||
| 88 | } | ||||
| 89 | } | ||||
| 90 | } | ||||
| 91 | |||||
| 92 | 1 | 100ns | my $persistent_count; | ||
| 93 | |||||
| 94 | sub NUM # (;$count,$show) | ||||
| 95 | { | ||||
| 96 | if (defined $_[0]) | ||||
| 97 | { | ||||
| 98 | $persistent_count = $_[0]; | ||||
| 99 | return $_[0] if !defined($_[1]) || $_[1]; | ||||
| 100 | } | ||||
| 101 | else | ||||
| 102 | { | ||||
| 103 | $persistent_count = undef; | ||||
| 104 | } | ||||
| 105 | return ''; | ||||
| 106 | } | ||||
| 107 | |||||
| 108 | |||||
| 109 | # 0. PERFORM GENERAL INFLECTIONS IN A STRING | ||||
| 110 | |||||
| 111 | 49 | 163µs | # spent 59µs within Lingua::EN::Inflect::enclose which was called 49 times, avg 1µs/call:
# 4 times (4µs+0s) by Pod::Wordlist::BEGIN@4 at line 613, avg 1µs/call
# once (4µs+0s) by Pod::Wordlist::BEGIN@4 at line 470
# once (4µs+0s) by Pod::Wordlist::BEGIN@4 at line 542
# once (3µs+0s) by Pod::Wordlist::BEGIN@4 at line 550
# once (2µs+0s) by Pod::Wordlist::BEGIN@4 at line 214
# once (2µs+0s) by Pod::Wordlist::BEGIN@4 at line 375
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 1315
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 719
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 680
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 270
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 596
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 693
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 231
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 274
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 222
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 619
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 476
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 451
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 581
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 248
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 298
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 463
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 291
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 359
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 722
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 768
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 531
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 1321
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 341
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 483
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 307
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 490
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 371
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 757
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 257
# once (1µs+0s) by Pod::Wordlist::BEGIN@4 at line 321
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 742
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 281
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 729
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 330
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 1326
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 747
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 736
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 458
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 497
# once (900ns+0s) by Pod::Wordlist::BEGIN@4 at line 349 | ||
| 112 | |||||
| 113 | sub inflect | ||||
| 114 | { | ||||
| 115 | my $save_persistent_count = $persistent_count; | ||||
| 116 | my @sections = split /(NUM\([^)]*\))/, $_[0]; | ||||
| 117 | my $inflection = ""; | ||||
| 118 | |||||
| 119 | foreach ( @sections ) | ||||
| 120 | { | ||||
| 121 | unless (s/NUM\(\s*?(?:([^),]*)(?:,([^)]*))?)?\)/ NUM($1,$2) /xe) | ||||
| 122 | { | ||||
| 123 | 1 while | ||||
| 124 | s/\bPL \( ([^),]*) (, ([^)]*) )? \) / PL($1,$3) /xeg | ||||
| 125 | || s/\bPL_N \( ([^),]*) (, ([^)]*) )? \) / PL_N($1,$3) /xeg | ||||
| 126 | || s/\bPL_V \( ([^),]*) (, ([^)]*) )? \) / PL_V($1,$3) /xeg | ||||
| 127 | || s/\bPL_ADJ \( ([^),]*) (, ([^)]*) )? \) / PL_ADJ($1,$3) /xeg | ||||
| 128 | || s/\bAN? \( ([^),]*) (, ([^)]*) )? \) / A($1,$3) /xeg | ||||
| 129 | || s/\bNO \( ([^),]*) (, ([^)]*) )? \) / NO($1,$3) /xeg | ||||
| 130 | || s/\bORD \( ([^)]*) \) / ORD($1) /xeg | ||||
| 131 | || s/\bNUMWORDS \( ([^)]*) \) / NUMWORDS($1) /xeg | ||||
| 132 | || s/\bPART_PRES \( ([^)]*) \) / PART_PRES($1) /xeg | ||||
| 133 | } | ||||
| 134 | |||||
| 135 | $inflection .= $_; | ||||
| 136 | } | ||||
| 137 | |||||
| 138 | $persistent_count = $save_persistent_count; | ||||
| 139 | return $inflection; | ||||
| 140 | } | ||||
| 141 | |||||
| 142 | |||||
| 143 | # 1. PLURALS | ||||
| 144 | |||||
| 145 | 1 | 9µs | my %PL_sb_irregular_s = | ||
| 146 | ( | ||||
| 147 | "corpus" => "corpuses|corpora", | ||||
| 148 | "opus" => "opuses|opera", | ||||
| 149 | "magnum opus" => "magnum opuses|magna opera", | ||||
| 150 | "genus" => "genera", | ||||
| 151 | "mythos" => "mythoi", | ||||
| 152 | "penis" => "penises|penes", | ||||
| 153 | "testis" => "testes", | ||||
| 154 | "atlas" => "atlases|atlantes", | ||||
| 155 | "yes" => "yeses", | ||||
| 156 | 'editio princeps' => 'editiones principes', | ||||
| 157 | 'starets' => 'startsy', | ||||
| 158 | 'staretz' => 'startzy', | ||||
| 159 | ); | ||||
| 160 | |||||
| 161 | 1 | 23µs | my %PL_sb_irregular = | ||
| 162 | ( | ||||
| 163 | "child" => "children", | ||||
| 164 | "brother" => "brothers|brethren", | ||||
| 165 | "loaf" => "loaves", | ||||
| 166 | "hoof" => "hoofs|hooves", | ||||
| 167 | "beef" => "beefs|beeves", | ||||
| 168 | "thief" => "thiefs|thieves", | ||||
| 169 | "money" => "monies", | ||||
| 170 | "mongoose" => "mongooses", | ||||
| 171 | "ox" => "oxen", | ||||
| 172 | "cow" => "cows|kine", | ||||
| 173 | "graffito" => "graffiti", | ||||
| 174 | "prima donna" => "prima donnas|prime donne", | ||||
| 175 | "octopus" => "octopuses|octopodes", | ||||
| 176 | "genie" => "genies|genii", | ||||
| 177 | "ganglion" => "ganglions|ganglia", | ||||
| 178 | "trilby" => "trilbys", | ||||
| 179 | "turf" => "turfs|turves", | ||||
| 180 | "numen" => "numina", | ||||
| 181 | "atman" => "atmas", | ||||
| 182 | "occiput" => "occiputs|occipita", | ||||
| 183 | 'sabretooth' => 'sabretooths', | ||||
| 184 | 'sabertooth' => 'sabertooths', | ||||
| 185 | 'lowlife' => 'lowlifes', | ||||
| 186 | 'flatfoot' => 'flatfoots', | ||||
| 187 | 'tenderfoot' => 'tenderfoots', | ||||
| 188 | 'Romany' => 'Romanies', | ||||
| 189 | 'romany' => 'romanies', | ||||
| 190 | 'Tornese' => 'Tornesi', | ||||
| 191 | 'Jerry' => 'Jerrys', | ||||
| 192 | 'jerry' => 'jerries', | ||||
| 193 | 'Mary' => 'Marys', | ||||
| 194 | 'mary' => 'maries', | ||||
| 195 | 'talouse' => 'talouses', | ||||
| 196 | 'blouse' => 'blouses', | ||||
| 197 | 'Rom' => 'Roma', | ||||
| 198 | 'rom' => 'roma', | ||||
| 199 | 'carmen' => 'carmina', | ||||
| 200 | 'cheval' => 'chevaux', | ||||
| 201 | 'chervonetz' => 'chervontzi', | ||||
| 202 | 'kuvasz' => 'kuvaszok', | ||||
| 203 | 'felo' => 'felones', | ||||
| 204 | 'put-off' => 'put-offs', | ||||
| 205 | 'set-off' => 'set-offs', | ||||
| 206 | 'set-out' => 'set-outs', | ||||
| 207 | 'set-to' => 'set-tos', | ||||
| 208 | 'brother-german' => 'brothers-german|brethren-german', | ||||
| 209 | 'studium generale' => 'studia generali', | ||||
| 210 | |||||
| 211 | %PL_sb_irregular_s, | ||||
| 212 | ); | ||||
| 213 | |||||
| 214 | 1 | 25µs | 2 | 12µs | my $PL_sb_irregular = enclose join '|', reverse sort keys %PL_sb_irregular; # spent 10µs making 1 call to Lingua::EN::Inflect::CORE:sort
# spent 2µs making 1 call to Lingua::EN::Inflect::enclose |
| 215 | |||||
| 216 | # Z's that don't double | ||||
| 217 | |||||
| 218 | 1 | 1µs | my @PL_sb_z_zes = | ||
| 219 | ( | ||||
| 220 | "batz", "quartz", "topaz", "snooz(?=e)", "kibbutz", | ||||
| 221 | ); | ||||
| 222 | 1 | 2µs | 1 | 1µs | my $PL_sb_z_zes = enclose join '|', @PL_sb_z_zes; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 223 | |||||
| 224 | # UNCONDITIONAL "..is" -> "..ides" | ||||
| 225 | |||||
| 226 | 1 | 400ns | my @PL_sb_U_is_ides = | ||
| 227 | ( | ||||
| 228 | "aphis", | ||||
| 229 | ); | ||||
| 230 | |||||
| 231 | 1 | 3µs | 1 | 1µs | my $PL_sb_U_is_ides = enclose join "|", map { substr($_,0,-2) } @PL_sb_U_is_ides; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 232 | |||||
| 233 | # CLASSICAL "..is" -> "..ides" | ||||
| 234 | |||||
| 235 | 1 | 1µs | my @PL_sb_C_is_ides = | ||
| 236 | ( | ||||
| 237 | # GENERAL WORDS... | ||||
| 238 | |||||
| 239 | "ephemeris", "iris", "clitoris", | ||||
| 240 | "chrysalis", "epididymis", | ||||
| 241 | |||||
| 242 | # INFLAMATIONS... | ||||
| 243 | |||||
| 244 | ".*itis", | ||||
| 245 | |||||
| 246 | ); | ||||
| 247 | |||||
| 248 | 1 | 4µs | 1 | 1µs | my $PL_sb_C_is_ides = enclose join "|", map { substr($_,0,-2) } @PL_sb_C_is_ides; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 249 | |||||
| 250 | # UNCONDITIONAL "..a" -> "..ata" | ||||
| 251 | |||||
| 252 | 1 | 600ns | my @PL_sb_U_a_ata = | ||
| 253 | ( | ||||
| 254 | "plasmalemma", "pseudostoma", | ||||
| 255 | ); | ||||
| 256 | |||||
| 257 | 1 | 2µs | 1 | 1µs | my $PL_sb_U_a_ata = enclose join "|", map { substr($_,0,-1) } @PL_sb_U_a_ata; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 258 | |||||
| 259 | # CLASSICAL "..a" -> "..ata" | ||||
| 260 | |||||
| 261 | 1 | 3µs | my @PL_sb_C_a_ata = | ||
| 262 | ( | ||||
| 263 | "anathema", "bema", "carcinoma", "charisma", "diploma", | ||||
| 264 | "dogma", "drama", "edema", "enema", "enigma", "lemma", | ||||
| 265 | "lymphoma", "magma", "melisma", "miasma", "oedema", | ||||
| 266 | "sarcoma", "schema", "soma", "stigma", "stoma", "trauma", | ||||
| 267 | "gumma", "pragma", "bema", | ||||
| 268 | ); | ||||
| 269 | |||||
| 270 | 1 | 13µs | 1 | 1µs | my $PL_sb_C_a_ata = enclose join "|", map { substr($_,0,-1) } @PL_sb_C_a_ata; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 271 | |||||
| 272 | # UNCONDITIONAL "..a" -> "..ae" | ||||
| 273 | |||||
| 274 | 1 | 1µs | 1 | 1µs | my $PL_sb_U_a_ae = enclose join "|", # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 275 | ( | ||||
| 276 | "alumna", "alga", "vertebra", "persona" | ||||
| 277 | ); | ||||
| 278 | |||||
| 279 | # CLASSICAL "..a" -> "..ae" | ||||
| 280 | |||||
| 281 | 1 | 2µs | 1 | 900ns | my $PL_sb_C_a_ae = enclose join "|", # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 282 | ( | ||||
| 283 | "amoeba", "antenna", "formula", "hyperbola", | ||||
| 284 | "medusa", "nebula", "parabola", "abscissa", | ||||
| 285 | "hydra", "nova", "lacuna", "aurora", ".*umbra", | ||||
| 286 | "flora", "fauna", | ||||
| 287 | ); | ||||
| 288 | |||||
| 289 | # CLASSICAL "..en" -> "..ina" | ||||
| 290 | |||||
| 291 | 1 | 3µs | 1 | 1µs | my $PL_sb_C_en_ina = enclose join "|", map { substr($_,0,-2) } # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 292 | ( | ||||
| 293 | "stamen", "foramen", "lumen" | ||||
| 294 | ); | ||||
| 295 | |||||
| 296 | # UNCONDITIONAL "..um" -> "..a" | ||||
| 297 | |||||
| 298 | 1 | 6µs | 1 | 1µs | my $PL_sb_U_um_a = enclose join "|", map { substr($_,0,-2) } # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 299 | ( | ||||
| 300 | "bacterium", "agendum", "desideratum", "erratum", | ||||
| 301 | "stratum", "datum", "ovum", "extremum", | ||||
| 302 | "candelabrum", "intermedium", "malum", "Progymnasium", | ||||
| 303 | ); | ||||
| 304 | |||||
| 305 | # CLASSICAL "..um" -> "..a" | ||||
| 306 | |||||
| 307 | 1 | 12µs | 1 | 1µs | my $PL_sb_C_um_a = enclose join "|", map { substr($_,0,-2) } # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 308 | ( | ||||
| 309 | "maximum", "minimum", "momentum", "optimum", | ||||
| 310 | "quantum", "cranium", "curriculum", "dictum", | ||||
| 311 | "phylum", "aquarium", "compendium", "emporium", | ||||
| 312 | "enconium", "gymnasium", "honorarium", "interregnum", | ||||
| 313 | "lustrum", "memorandum", "millennium", "rostrum", | ||||
| 314 | "spectrum", "speculum", "stadium", "trapezium", | ||||
| 315 | "ultimatum", "medium", "vacuum", "velum", | ||||
| 316 | "consortium", | ||||
| 317 | ); | ||||
| 318 | |||||
| 319 | # UNCONDITIONAL "..us" -> "i" | ||||
| 320 | |||||
| 321 | 1 | 6µs | 1 | 1µs | my $PL_sb_U_us_i = enclose join "|", map { substr($_,0,-2) } # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 322 | ( | ||||
| 323 | "alumnus", "alveolus", "bacillus", "bronchus", | ||||
| 324 | "locus", "nucleus", "stimulus", "meniscus", | ||||
| 325 | "sarcophagus", "interradius", "perradius", "triradius", | ||||
| 326 | ); | ||||
| 327 | |||||
| 328 | # CLASSICAL "..us" -> "..i" | ||||
| 329 | |||||
| 330 | 1 | 7µs | 1 | 900ns | my $PL_sb_C_us_i = enclose join "|", map { substr($_,0,-2) } # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 331 | ( | ||||
| 332 | "focus", "radius", "genius", | ||||
| 333 | "incubus", "succubus", "nimbus", | ||||
| 334 | "fungus", "nucleolus", "stylus", | ||||
| 335 | "torus", "umbilicus", "uterus", | ||||
| 336 | "hippopotamus", "cactus", | ||||
| 337 | ); | ||||
| 338 | |||||
| 339 | # CLASSICAL "..us" -> "..us" (ASSIMILATED 4TH DECLENSION LATIN NOUNS) | ||||
| 340 | |||||
| 341 | 1 | 1µs | 1 | 1µs | my $PL_sb_C_us_us = enclose join "|", # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 342 | ( | ||||
| 343 | "status", "apparatus", "prospectus", "sinus", | ||||
| 344 | "hiatus", "impetus", "plexus", | ||||
| 345 | ); | ||||
| 346 | |||||
| 347 | # UNCONDITIONAL "..on" -> "a" | ||||
| 348 | |||||
| 349 | 1 | 5µs | 1 | 900ns | my $PL_sb_U_on_a = enclose join "|", map { substr($_,0,-2) } # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 350 | ( | ||||
| 351 | "criterion", "perihelion", "aphelion", | ||||
| 352 | "phenomenon", "prolegomenon", "noumenon", | ||||
| 353 | "organon", "asyndeton", "hyperbaton", | ||||
| 354 | "legomenon", | ||||
| 355 | ); | ||||
| 356 | |||||
| 357 | # CLASSICAL "..on" -> "..a" | ||||
| 358 | |||||
| 359 | 1 | 2µs | 1 | 1µs | my $PL_sb_C_on_a = enclose join "|", map { substr($_,0,-2) } # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 360 | ( | ||||
| 361 | "oxymoron", | ||||
| 362 | ); | ||||
| 363 | |||||
| 364 | # CLASSICAL "..o" -> "..i" (BUT NORMALLY -> "..os") | ||||
| 365 | |||||
| 366 | 1 | 2µs | my @PL_sb_C_o_i = | ||
| 367 | ( | ||||
| 368 | "solo", "soprano", "basso", "alto", | ||||
| 369 | "contralto", "tempo", "piano", "virtuoso", | ||||
| 370 | ); | ||||
| 371 | 1 | 4µs | 1 | 1µs | my $PL_sb_C_o_i = enclose join "|", map { substr($_,0,-1) } @PL_sb_C_o_i; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 372 | |||||
| 373 | # ALWAYS "..o" -> "..os" | ||||
| 374 | |||||
| 375 | 1 | 11µs | 1 | 2µs | my $PL_sb_U_o_os = enclose join "|", # spent 2µs making 1 call to Lingua::EN::Inflect::enclose |
| 376 | ( | ||||
| 377 | "^ado", "aficionado", "aggro", | ||||
| 378 | "albino", "allegro", "ammo", | ||||
| 379 | "Antananarivo", "archipelago", "armadillo", | ||||
| 380 | "auto", "avocado", "Bamako", | ||||
| 381 | "Barquisimeto", "bimbo", "bingo", | ||||
| 382 | "Biro", "bolero", "Bolzano", | ||||
| 383 | "bongo", "Boto", "burro", | ||||
| 384 | "Cairo", "canto", "cappuccino", | ||||
| 385 | "casino", "cello", "Chicago", | ||||
| 386 | "Chimango", "cilantro", "cochito", | ||||
| 387 | "coco", "Colombo", "Colorado", | ||||
| 388 | "commando", "concertino", "contango", | ||||
| 389 | "credo", "crescendo", "cyano", | ||||
| 390 | "demo", "ditto", "Draco", | ||||
| 391 | "dynamo", "embryo", "Esperanto", | ||||
| 392 | "espresso", "euro", "falsetto", | ||||
| 393 | "Faro", "fiasco", "Filipino", | ||||
| 394 | "flamenco", "furioso", "generalissimo", | ||||
| 395 | "Gestapo", "ghetto", "gigolo", | ||||
| 396 | "gizmo", "Greensboro", "gringo", | ||||
| 397 | "Guaiabero", "guano", "gumbo", | ||||
| 398 | "gyro", "hairdo", "hippo", | ||||
| 399 | "Idaho", "impetigo", "inferno", | ||||
| 400 | "info", "intermezzo", "intertrigo", | ||||
| 401 | "Iquico", "^ISO", "jumbo", | ||||
| 402 | "junto", "Kakapo", "kilo", | ||||
| 403 | "Kinkimavo", "Kokako", "Kosovo", | ||||
| 404 | "Lesotho", "libero", "libido", | ||||
| 405 | "libretto", "lido", "Lilo", | ||||
| 406 | "limbo", "limo", "lineno", | ||||
| 407 | "lingo", "lino", "livedo", | ||||
| 408 | "loco", "logo", "lumbago", | ||||
| 409 | "macho", "macro", "mafioso", | ||||
| 410 | "magneto", "magnifico", "Majuro", | ||||
| 411 | "Malabo", "manifesto", "Maputo", | ||||
| 412 | "Maracaibo", "medico", "memo", | ||||
| 413 | "metro", "Mexico", "micro", | ||||
| 414 | "Milano", "Monaco", "mono", | ||||
| 415 | "Montenegro", "Morocco", "Muqdisho", | ||||
| 416 | "myo", "^NATO", "^NCO", | ||||
| 417 | "neutrino", "^NGO", "Ningbo", | ||||
| 418 | "octavo", "oregano", "Orinoco", | ||||
| 419 | "Orlando", "Oslo", "^oto", | ||||
| 420 | "panto", "Paramaribo", "Pardusco", | ||||
| 421 | "pedalo", "photo", "pimento", | ||||
| 422 | "pinto", "pleco", "Pluto", | ||||
| 423 | "pogo", "polo", "poncho", | ||||
| 424 | "Porto-Novo", "Porto", "pro", | ||||
| 425 | "psycho", "pueblo", "quarto", | ||||
| 426 | "Quito", "rhino", "risotto", | ||||
| 427 | "rococo", "rondo", "Sacramento", | ||||
| 428 | "saddo", "sago", "salvo", | ||||
| 429 | "Santiago", "Sapporo", "Sarajevo", | ||||
| 430 | "scherzando", "scherzo", "silo", | ||||
| 431 | "sirocco", "sombrero", "staccato", | ||||
| 432 | "sterno", "stucco", "stylo", | ||||
| 433 | "sumo", "Taiko", "techno", | ||||
| 434 | "terrazzo", "testudo", "timpano", | ||||
| 435 | "tiro", "tobacco", "Togo", | ||||
| 436 | "Tokyo", "torero", "Torino", | ||||
| 437 | "Toronto", "torso", "tremolo", | ||||
| 438 | "typo", "tyro", "ufo", | ||||
| 439 | "UNESCO", "vaquero", "vermicello", | ||||
| 440 | "verso", "vibrato", "violoncello", | ||||
| 441 | "Virgo", "weirdo", "WHO", | ||||
| 442 | "WTO", "Yamoussoukro", "yo-yo", | ||||
| 443 | "zero", "Zibo", | ||||
| 444 | |||||
| 445 | @PL_sb_C_o_i, | ||||
| 446 | ); | ||||
| 447 | |||||
| 448 | |||||
| 449 | # UNCONDITIONAL "..ch" -> "..chs" | ||||
| 450 | |||||
| 451 | 1 | 3µs | 1 | 1µs | my $PL_sb_U_ch_chs = enclose join "|", map { substr($_,0,-2) } # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 452 | qw( | ||||
| 453 | czech eunuch stomach | ||||
| 454 | ); | ||||
| 455 | |||||
| 456 | # UNCONDITIONAL "..[ei]x" -> "..ices" | ||||
| 457 | |||||
| 458 | 1 | 2µs | 1 | 900ns | my $PL_sb_U_ex_ices = enclose join "|", map { substr($_,0,-2) } # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 459 | ( | ||||
| 460 | "codex", "murex", "silex", | ||||
| 461 | ); | ||||
| 462 | |||||
| 463 | 1 | 2µs | 1 | 1µs | my $PL_sb_U_ix_ices = enclose join "|", map { substr($_,0,-2) } # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 464 | ( | ||||
| 465 | "radix", "helix", | ||||
| 466 | ); | ||||
| 467 | |||||
| 468 | # CLASSICAL "..[ei]x" -> "..ices" | ||||
| 469 | |||||
| 470 | 1 | 7µs | 1 | 4µs | my $PL_sb_C_ex_ices = enclose join "|", map { substr($_,0,-2) } # spent 4µs making 1 call to Lingua::EN::Inflect::enclose |
| 471 | ( | ||||
| 472 | "vortex", "vertex", "cortex", "latex", | ||||
| 473 | "pontifex", "apex", "index", "simplex", | ||||
| 474 | ); | ||||
| 475 | |||||
| 476 | 1 | 2µs | 1 | 1µs | my $PL_sb_C_ix_ices = enclose join "|", map { substr($_,0,-2) } # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 477 | ( | ||||
| 478 | "appendix", | ||||
| 479 | ); | ||||
| 480 | |||||
| 481 | # ARABIC: ".." -> "..i" | ||||
| 482 | |||||
| 483 | 1 | 1µs | 1 | 1µs | my $PL_sb_C_i = enclose join "|", # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 484 | ( | ||||
| 485 | "afrit", "afreet", "efreet", | ||||
| 486 | ); | ||||
| 487 | |||||
| 488 | # HEBREW: ".." -> "..im" | ||||
| 489 | |||||
| 490 | 1 | 1µs | 1 | 1µs | my $PL_sb_C_im = enclose join "|", # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 491 | ( | ||||
| 492 | "goy", "seraph", "cherub", "zuz", "kibbutz", | ||||
| 493 | ); | ||||
| 494 | |||||
| 495 | # UNCONDITIONAL "..man" -> "..mans" | ||||
| 496 | |||||
| 497 | 1 | 3µs | 1 | 900ns | my $PL_sb_U_man_mans = enclose join "|", # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 498 | qw( | ||||
| 499 | \bataman caiman cayman ceriman | ||||
| 500 | \bdesman \bdolman \bfarman \bharman \bhetman | ||||
| 501 | human \bleman ottoman shaman talisman | ||||
| 502 | Alabaman Bahaman Burman German | ||||
| 503 | Hiroshiman Liman Nakayaman Norman Oklahoman | ||||
| 504 | Panaman Roman Selman Sonaman Tacoman Yakiman | ||||
| 505 | Yokohaman Yuman | ||||
| 506 | ); | ||||
| 507 | |||||
| 508 | 1 | 5µs | my @PL_sb_uninflected_s = | ||
| 509 | ( | ||||
| 510 | # PAIRS OR GROUPS SUBSUMED TO A SINGULAR... | ||||
| 511 | "breeches", "britches", "pajamas", "pyjamas", "clippers", "gallows", | ||||
| 512 | "hijinks", "headquarters", "pliers", "scissors", "testes", "herpes", | ||||
| 513 | "pincers", "shears", "proceedings", "trousers", | ||||
| 514 | |||||
| 515 | # UNASSIMILATED LATIN 4th DECLENSION | ||||
| 516 | |||||
| 517 | "cantus", "coitus", "nexus", | ||||
| 518 | |||||
| 519 | # RECENT IMPORTS... | ||||
| 520 | "contretemps", "corps", "debris", | ||||
| 521 | ".*ois", "siemens", | ||||
| 522 | |||||
| 523 | # DISEASES | ||||
| 524 | ".*measles", "mumps", | ||||
| 525 | |||||
| 526 | # MISCELLANEOUS OTHERS... | ||||
| 527 | "diabetes", "jackanapes", ".*series", "species", "rabies", | ||||
| 528 | "chassis", "innings", "news", "mews", "haggis", | ||||
| 529 | ); | ||||
| 530 | |||||
| 531 | 1 | 2µs | 1 | 1µs | my $PL_sb_uninflected_herd = enclose join "|", # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 532 | # DON'T INFLECT IN CLASSICAL MODE, OTHERWISE NORMAL INFLECTION | ||||
| 533 | ( | ||||
| 534 | "wildebeest", "swine", "eland", "bison", "buffalo", | ||||
| 535 | "elk", "rhinoceros", 'zucchini', | ||||
| 536 | 'caribou', 'dace', 'grouse', 'guinea[- ]fowl', | ||||
| 537 | 'haddock', 'hake', 'halibut', 'herring', 'mackerel', | ||||
| 538 | 'pickerel', 'pike', 'roe', 'seed', 'shad', | ||||
| 539 | 'snipe', 'teal', 'turbot', 'water[- ]fowl', | ||||
| 540 | ); | ||||
| 541 | |||||
| 542 | 1 | 1µs | 1 | 4µs | my $PL_sb_lese_lesen = enclose join "|", # spent 4µs making 1 call to Lingua::EN::Inflect::enclose |
| 543 | ( | ||||
| 544 | 'Auslese', | ||||
| 545 | 'beerenauslese', | ||||
| 546 | 'Spaetlese', | ||||
| 547 | 'trockenbeerenauslese', | ||||
| 548 | ); | ||||
| 549 | |||||
| 550 | 1 | 5µs | 1 | 3µs | my $PL_sb_uninflected = enclose join "|", # spent 3µs making 1 call to Lingua::EN::Inflect::enclose |
| 551 | ( | ||||
| 552 | # SOME FISH AND HERD ANIMALS | ||||
| 553 | ".*fish", "tuna", "salmon", "mackerel", "trout", | ||||
| 554 | "bream", "sea[- ]bass", "carp", "cod", "flounder", "whiting", | ||||
| 555 | |||||
| 556 | ".*deer", ".*sheep", "moose", | ||||
| 557 | |||||
| 558 | # ALL NATIONALS ENDING IN -ese | ||||
| 559 | "Portuguese", "Amoyese", "Borghese", "Congoese", "Faroese", | ||||
| 560 | "Foochowese", "Genevese", "Genoese", "Gilbertese", "Hottentotese", | ||||
| 561 | "Kiplingese", "Kongoese", "Lucchese", "Maltese", "Nankingese", | ||||
| 562 | "Niasese", "Pekingese", "Piedmontese", "Pistoiese", "Sarawakese", | ||||
| 563 | "Shavese", "Vermontese", "Wenchowese", "Yengeese", | ||||
| 564 | ".*[nrlm]ese", | ||||
| 565 | |||||
| 566 | # SOME WORDS ENDING IN ...s (OFTEN PAIRS TAKEN AS A WHOLE) | ||||
| 567 | |||||
| 568 | @PL_sb_uninflected_s, | ||||
| 569 | |||||
| 570 | # DISEASES | ||||
| 571 | ".*pox", | ||||
| 572 | |||||
| 573 | |||||
| 574 | # OTHER ODDITIES | ||||
| 575 | "graffiti", "djinn", 'samuri', | ||||
| 576 | '.*craft$', 'offspring', 'pence', 'quid', 'hertz', | ||||
| 577 | ); | ||||
| 578 | |||||
| 579 | # SINGULAR WORDS ENDING IN ...s (ALL INFLECT WITH ...es) | ||||
| 580 | |||||
| 581 | 1 | 4µs | 1 | 1µs | my $PL_sb_singular_s = enclose join '|', # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 582 | ( | ||||
| 583 | ".*ss", | ||||
| 584 | "acropolis", "aegis", "alias", "asbestos", "bathos", "bias", | ||||
| 585 | "bronchitis", "bursitis", "caddis", "cannabis", | ||||
| 586 | "canvas", "chaos", "cosmos", "dais", "digitalis", | ||||
| 587 | "epidermis", "ethos", "eyas", "gas", "glottis", | ||||
| 588 | "hubris", "ibis", "lens", "mantis", "marquis", "metropolis", | ||||
| 589 | "pathos", "pelvis", "polis", "rhinoceros", | ||||
| 590 | "sassafras", "trellis", ".*us", "[A-Z].*es", | ||||
| 591 | |||||
| 592 | @PL_sb_C_is_ides, | ||||
| 593 | @PL_sb_U_is_ides, | ||||
| 594 | ); | ||||
| 595 | |||||
| 596 | 1 | 5µs | 1 | 1µs | my $PL_v_special_s = enclose join '|', # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 597 | ( | ||||
| 598 | $PL_sb_singular_s, | ||||
| 599 | @PL_sb_uninflected_s, | ||||
| 600 | keys %PL_sb_irregular_s, | ||||
| 601 | '(.*[csx])is', | ||||
| 602 | '(.*)ceps', | ||||
| 603 | '[A-Z].*s', | ||||
| 604 | ); | ||||
| 605 | |||||
| 606 | 1 | 2µs | my %PL_sb_postfix_adj = ( | ||
| 607 | 'general' => ['(?!major|lieutenant|brigadier|adjutant|.*star)\S+'], | ||||
| 608 | 'martial' => [qw(court)], | ||||
| 609 | ); | ||||
| 610 | |||||
| 611 | 1 | 1µs | foreach (keys %PL_sb_postfix_adj) { | ||
| 612 | $PL_sb_postfix_adj{$_} = enclose | ||||
| 613 | 2 | 8µs | 4 | 4µs | enclose(join('|', @{$PL_sb_postfix_adj{$_}})) # spent 4µs making 4 calls to Lingua::EN::Inflect::enclose, avg 1µs/call |
| 614 | . "(?=(?:-|\\s+)$_)"; | ||||
| 615 | } | ||||
| 616 | |||||
| 617 | 1 | 4µs | my $PL_sb_postfix_adj = '(' . join('|', values %PL_sb_postfix_adj) . ')(.*)'; | ||
| 618 | |||||
| 619 | 1 | 6µs | 1 | 1µs | my $PL_prep = enclose join '|', qw ( # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 620 | about above across after against amid amidst among around as at athwart atop | ||||
| 621 | barring before behind below beneath beside besides between betwixt beyond but by | ||||
| 622 | circa | ||||
| 623 | despite down during | ||||
| 624 | except | ||||
| 625 | failing for from | ||||
| 626 | given | ||||
| 627 | in inside into | ||||
| 628 | like | ||||
| 629 | minus | ||||
| 630 | near next | ||||
| 631 | of off on onto out outside over | ||||
| 632 | pace past per plus pro | ||||
| 633 | qua | ||||
| 634 | round | ||||
| 635 | sans save since | ||||
| 636 | than through throughout thru thruout till times to toward towards | ||||
| 637 | under underneath unlike until unto up upon | ||||
| 638 | versus via vs | ||||
| 639 | with within without worth | ||||
| 640 | ); | ||||
| 641 | |||||
| 642 | 1 | 1µs | my $PL_sb_prep_dual_compound = '(.*?)((?:-|\s+)(?:'.$PL_prep.'|d[eua])(?:-|\s+))a(?:-|\s+)(.*)'; | ||
| 643 | |||||
| 644 | 1 | 800ns | my $PL_sb_prep_compound = '(.*?)((-|\s+)('.$PL_prep.'|d[eua])((-|\s+)(.*))?)'; | ||
| 645 | |||||
| 646 | |||||
| 647 | 1 | 10µs | my %PL_pron_nom = | ||
| 648 | ( | ||||
| 649 | # NOMINATIVE REFLEXIVE | ||||
| 650 | |||||
| 651 | "i" => "we", "myself" => "ourselves", | ||||
| 652 | "you" => "you", "yourself" => "yourselves", | ||||
| 653 | "she" => "they", "herself" => "themselves", | ||||
| 654 | "he" => "they", "himself" => "themselves", | ||||
| 655 | "it" => "they", "itself" => "themselves", | ||||
| 656 | "they" => "they", "themself" => "themselves", | ||||
| 657 | |||||
| 658 | # POSSESSIVE | ||||
| 659 | |||||
| 660 | "mine" => "ours", | ||||
| 661 | "yours" => "yours", | ||||
| 662 | "hers" => "theirs", | ||||
| 663 | "his" => "theirs", | ||||
| 664 | "its" => "theirs", | ||||
| 665 | "theirs" => "theirs", | ||||
| 666 | ); | ||||
| 667 | |||||
| 668 | 1 | 4µs | my %PL_pron_acc = | ||
| 669 | ( | ||||
| 670 | # ACCUSATIVE REFLEXIVE | ||||
| 671 | |||||
| 672 | "me" => "us", "myself" => "ourselves", | ||||
| 673 | "you" => "you", "yourself" => "yourselves", | ||||
| 674 | "her" => "them", "herself" => "themselves", | ||||
| 675 | "him" => "them", "himself" => "themselves", | ||||
| 676 | "it" => "them", "itself" => "themselves", | ||||
| 677 | "them" => "them", "themself" => "themselves", | ||||
| 678 | ); | ||||
| 679 | |||||
| 680 | 1 | 3µs | 1 | 1µs | my $PL_pron_acc = enclose join '|', keys %PL_pron_acc; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 681 | |||||
| 682 | 1 | 5µs | my %PL_v_irregular_pres = | ||
| 683 | ( | ||||
| 684 | # 1st PERS. SING. 2ND PERS. SING. 3RD PERS. SINGULAR | ||||
| 685 | # 3RD PERS. (INDET.) | ||||
| 686 | |||||
| 687 | "am" => "are", "are" => "are", "is" => "are", | ||||
| 688 | "was" => "were", "were" => "were", "was" => "were", | ||||
| 689 | "have" => "have", "have" => "have", "has" => "have", | ||||
| 690 | "do" => "do", "do" => "do", "does" => "do", | ||||
| 691 | ); | ||||
| 692 | |||||
| 693 | 1 | 2µs | 1 | 1µs | my $PL_v_irregular_pres = enclose join '|', keys %PL_v_irregular_pres; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 694 | |||||
| 695 | 1 | 22µs | my %PL_v_ambiguous_pres = | ||
| 696 | ( | ||||
| 697 | # 1st PERS. SING. 2ND PERS. SING. 3RD PERS. SINGULAR | ||||
| 698 | # 3RD PERS. (INDET.) | ||||
| 699 | |||||
| 700 | "act" => "act", "act" => "act", "acts" => "act", | ||||
| 701 | "blame" => "blame", "blame" => "blame", "blames" => "blame", | ||||
| 702 | "can" => "can", "can" => "can", "can" => "can", | ||||
| 703 | "must" => "must", "must" => "must", "must" => "must", | ||||
| 704 | "fly" => "fly", "fly" => "fly", "flies" => "fly", | ||||
| 705 | "copy" => "copy", "copy" => "copy", "copies" => "copy", | ||||
| 706 | "drink" => "drink", "drink" => "drink", "drinks" => "drink", | ||||
| 707 | "fight" => "fight", "fight" => "fight", "fights" => "fight", | ||||
| 708 | "fire" => "fire", "fire" => "fire", "fires" => "fire", | ||||
| 709 | "like" => "like", "like" => "like", "likes" => "like", | ||||
| 710 | "look" => "look", "look" => "look", "looks" => "look", | ||||
| 711 | "make" => "make", "make" => "make", "makes" => "make", | ||||
| 712 | "reach" => "reach", "reach" => "reach", "reaches" => "reach", | ||||
| 713 | "run" => "run", "run" => "run", "runs" => "run", | ||||
| 714 | "sink" => "sink", "sink" => "sink", "sinks" => "sink", | ||||
| 715 | "sleep" => "sleep", "sleep" => "sleep", "sleeps" => "sleep", | ||||
| 716 | "view" => "view", "view" => "view", "views" => "view", | ||||
| 717 | ); | ||||
| 718 | |||||
| 719 | 1 | 5µs | 1 | 1µs | my $PL_v_ambiguous_pres = enclose join '|', keys %PL_v_ambiguous_pres; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 720 | |||||
| 721 | |||||
| 722 | 1 | 2µs | 1 | 1µs | my $PL_v_irregular_non_pres = enclose join '|', # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 723 | ( | ||||
| 724 | "did", "had", "ate", "made", "put", | ||||
| 725 | "spent", "fought", "sank", "gave", "sought", | ||||
| 726 | "shall", "could", "ought", "should", | ||||
| 727 | ); | ||||
| 728 | |||||
| 729 | 1 | 1µs | 1 | 900ns | my $PL_v_ambiguous_non_pres = enclose join '|', # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 730 | ( | ||||
| 731 | "thought", "saw", "bent", "will", "might", "cut", | ||||
| 732 | ); | ||||
| 733 | |||||
| 734 | # "..oes" -> "..oe" (the rest are "..oes" -> "o") | ||||
| 735 | |||||
| 736 | 1 | 2µs | 1 | 900ns | my $PL_v_oes_oe = enclose join "|", # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 737 | qw( | ||||
| 738 | .*shoes .*hoes .*toes | ||||
| 739 | canoes floes oboes roes throes woes | ||||
| 740 | ); | ||||
| 741 | |||||
| 742 | 1 | 2µs | 1 | 900ns | my $PL_count_zero = enclose join '|', # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 743 | ( | ||||
| 744 | 0, "no", "zero", "nil" | ||||
| 745 | ); | ||||
| 746 | |||||
| 747 | 1 | 2µs | 1 | 900ns | my $PL_count_one = enclose join '|', # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 748 | ( | ||||
| 749 | 1, "a", "an", "one", "each", "every", "this", "that", | ||||
| 750 | ); | ||||
| 751 | |||||
| 752 | 1 | 2µs | my %PL_adj_special = | ||
| 753 | ( | ||||
| 754 | "a" => "some", "an" => "some", | ||||
| 755 | "this" => "these", "that" => "those", | ||||
| 756 | ); | ||||
| 757 | 1 | 2µs | 1 | 1µs | my $PL_adj_special = enclose join '|', keys %PL_adj_special; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 758 | |||||
| 759 | 1 | 2µs | my %PL_adj_poss = | ||
| 760 | ( | ||||
| 761 | "my" => "our", | ||||
| 762 | "your" => "your", | ||||
| 763 | "its" => "their", | ||||
| 764 | "her" => "their", | ||||
| 765 | "his" => "their", | ||||
| 766 | "their" => "their", | ||||
| 767 | ); | ||||
| 768 | 1 | 2µs | 1 | 1µs | my $PL_adj_poss = enclose join '|', keys %PL_adj_poss; # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 769 | |||||
| 770 | |||||
| 771 | sub checkpat | ||||
| 772 | { | ||||
| 773 | local $SIG{__WARN__} = sub {0}; | ||||
| 774 | do {$@ =~ s/at.*?$//; | ||||
| 775 | die "\nBad user-defined singular pattern:\n\t$@\n"} | ||||
| 776 | if (!eval "'' =~ m/$_[0]/; 1;" or $@); | ||||
| 777 | return @_; | ||||
| 778 | } | ||||
| 779 | |||||
| 780 | sub checkpatsubs | ||||
| 781 | { | ||||
| 782 | checkpat($_[0]); | ||||
| 783 | if (defined $_[1]) | ||||
| 784 | { | ||||
| 785 | local $SIG{__WARN__} = sub {0}; | ||||
| 786 | do {$@ =~ s/at.*?$//; | ||||
| 787 | die "\nBad user-defined plural string: '$_[1]'\n\t$@\n"} | ||||
| 788 | if (!eval "qq{$_[1]}; 1;" or $@); | ||||
| 789 | } | ||||
| 790 | return @_; | ||||
| 791 | } | ||||
| 792 | |||||
| 793 | 1 | 300ns | my @PL_sb_user_defined = (); | ||
| 794 | 1 | 100ns | my @PL_v_user_defined = (); | ||
| 795 | 1 | 100ns | my @PL_adj_user_defined = (); | ||
| 796 | 1 | 100ns | my @A_a_user_defined = (); | ||
| 797 | |||||
| 798 | sub def_noun | ||||
| 799 | { | ||||
| 800 | unshift @PL_sb_user_defined, checkpatsubs(@_); | ||||
| 801 | return 1; | ||||
| 802 | } | ||||
| 803 | |||||
| 804 | sub def_verb | ||||
| 805 | { | ||||
| 806 | unshift @PL_v_user_defined, checkpatsubs(@_[4,5]); | ||||
| 807 | unshift @PL_v_user_defined, checkpatsubs(@_[2,3]); | ||||
| 808 | unshift @PL_v_user_defined, checkpatsubs(@_[0,1]); | ||||
| 809 | return 1; | ||||
| 810 | } | ||||
| 811 | |||||
| 812 | sub def_adj | ||||
| 813 | { | ||||
| 814 | unshift @PL_adj_user_defined, checkpatsubs(@_); | ||||
| 815 | return 1; | ||||
| 816 | } | ||||
| 817 | |||||
| 818 | sub def_a | ||||
| 819 | { | ||||
| 820 | unshift @A_a_user_defined, checkpat(@_,'a'); | ||||
| 821 | return 1; | ||||
| 822 | } | ||||
| 823 | |||||
| 824 | sub def_an | ||||
| 825 | { | ||||
| 826 | unshift @A_a_user_defined, checkpat(@_,'an'); | ||||
| 827 | return 1; | ||||
| 828 | } | ||||
| 829 | |||||
| 830 | sub ud_match | ||||
| 831 | # spent 6.66ms within Lingua::EN::Inflect::ud_match which was called 3619 times, avg 2µs/call:
# 1220 times (2.48ms+0s) by Lingua::EN::Inflect::_PL_special_adjective at line 1272, avg 2µs/call
# 1220 times (2.23ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1188, avg 2µs/call
# 1179 times (1.95ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1033, avg 2µs/call | ||||
| 832 | 3619 | 726µs | my $word = shift; | ||
| 833 | 3619 | 1.76ms | for (my $i=0; $i < @_; $i+=2) | ||
| 834 | { | ||||
| 835 | if ($word =~ /^(?:$_[$i])$/i) | ||||
| 836 | { | ||||
| 837 | last unless defined $_[$i+1]; | ||||
| 838 | return eval '"'.$_[$i+1].'"'; | ||||
| 839 | } | ||||
| 840 | } | ||||
| 841 | 3619 | 8.49ms | return undef; | ||
| 842 | } | ||||
| 843 | |||||
| 844 | do | ||||
| 845 | 1 | 200ns | { | ||
| 846 | 1 | 6µs | local $SIG{__WARN__} = sub {0}; | ||
| 847 | 1 | 100ns | my $rcfile; | ||
| 848 | |||||
| 849 | 1 | 700ns | $rcfile = $INC{'Lingua//EN/Inflect.pm'} || ''; | ||
| 850 | 1 | 5µs | 1 | 600ns | $rcfile =~ s/Inflect.pm$/.inflectrc/; # spent 600ns making 1 call to Lingua::EN::Inflect::CORE:subst |
| 851 | 1 | 100ns | do $rcfile or die "\nBad .inflectrc file ($rcfile):\n\t$@\n" | ||
| 852 | if $rcfile && -r $rcfile && -s $rcfile; | ||||
| 853 | |||||
| 854 | 1 | 1µs | $rcfile = "$ENV{HOME}/.inflectrc" || ''; | ||
| 855 | 1 | 15µs | 1 | 6µs | do $rcfile or die "\nBad .inflectrc file ($rcfile):\n\t$@\n" # spent 6µs making 1 call to Lingua::EN::Inflect::CORE:fteread |
| 856 | if $rcfile && -r $rcfile && -s $rcfile; | ||||
| 857 | }; | ||||
| 858 | |||||
| 859 | sub postprocess # FIX PEDANTRY AND CAPITALIZATION :-) | ||||
| 860 | # spent 13.0ms (10.8+2.19) within Lingua::EN::Inflect::postprocess which was called 1220 times, avg 11µs/call:
# 1220 times (10.8ms+2.19ms) by Lingua::EN::Inflect::PL at line 875, avg 11µs/call | ||||
| 861 | 1220 | 400µs | my ($orig, $inflected) = @_; | ||
| 862 | 1220 | 4.74ms | 1220 | 577µs | $inflected =~ s/([^|]+)\|(.+)/ $classical{all}?$2:$1 /e; # spent 577µs making 1220 calls to Lingua::EN::Inflect::CORE:subst, avg 473ns/call |
| 863 | 1220 | 8.01ms | 3612 | 1.62ms | return $orig =~ /^I$/ ? $inflected # spent 1.62ms making 3612 calls to Lingua::EN::Inflect::CORE:match, avg 447ns/call |
| 864 | : $orig =~ /^[A-Z]+$/ ? uc $inflected | ||||
| 865 | : $orig =~ /^[A-Z]/ ? ucfirst $inflected | ||||
| 866 | : $inflected; | ||||
| 867 | } | ||||
| 868 | |||||
| 869 | sub PL | ||||
| 870 | # PL($word,$number) | ||||
| 871 | # spent 675ms (18.7+656) within Lingua::EN::Inflect::PL which was called 1220 times, avg 553µs/call:
# 1220 times (18.7ms+656ms) by Pod::Spell::BEGIN@10 at line 24 of Pod/Wordlist.pm, avg 553µs/call | ||||
| 872 | 1220 | 275µs | my ($str, $count) = @_; | ||
| 873 | 1220 | 8.21ms | 1220 | 3.17ms | my ($pre, $word, $post) = ($str =~ m/\A(\s*)(.+?)(\s*)\Z/); # spent 3.17ms making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 874 | 1220 | 125µs | return $str unless $word; | ||
| 875 | 1220 | 5.81ms | 4839 | 653ms | my $plural = postprocess $word, _PL_special_adjective($word,$count) # spent 511ms making 1179 calls to Lingua::EN::Inflect::_PL_noun, avg 434µs/call
# spent 98.4ms making 1220 calls to Lingua::EN::Inflect::_PL_special_verb, avg 81µs/call
# spent 30.3ms making 1220 calls to Lingua::EN::Inflect::_PL_special_adjective, avg 25µs/call
# spent 13.0ms making 1220 calls to Lingua::EN::Inflect::postprocess, avg 11µs/call |
| 876 | || _PL_special_verb($word,$count) | ||||
| 877 | || _PL_noun($word,$count); | ||||
| 878 | 1220 | 2.47ms | return $pre.$plural.$post; | ||
| 879 | } | ||||
| 880 | |||||
| 881 | sub PL_N | ||||
| 882 | # PL_N($word,$number) | ||||
| 883 | { | ||||
| 884 | my ($str, $count) = @_; | ||||
| 885 | my ($pre, $word, $post) = ($str =~ m/\A(\s*)(.+?)(\s*)\Z/); | ||||
| 886 | return $str unless $word; | ||||
| 887 | my $plural = postprocess $word, _PL_noun($word,$count); | ||||
| 888 | return $pre.$plural.$post; | ||||
| 889 | } | ||||
| 890 | |||||
| 891 | sub PL_V | ||||
| 892 | # PL_V($word,$number) | ||||
| 893 | { | ||||
| 894 | my ($str, $count) = @_; | ||||
| 895 | my ($pre, $word, $post) = ($str =~ m/\A(\s*)(.+?)(\s*)\Z/); | ||||
| 896 | return $str unless $word; | ||||
| 897 | my $plural = postprocess $word, _PL_special_verb($word,$count) | ||||
| 898 | || _PL_general_verb($word,$count); | ||||
| 899 | return $pre.$plural.$post; | ||||
| 900 | } | ||||
| 901 | |||||
| 902 | sub PL_ADJ | ||||
| 903 | # PL_ADJ($word,$number) | ||||
| 904 | { | ||||
| 905 | my ($str, $count) = @_; | ||||
| 906 | my ($pre, $word, $post) = ($str =~ m/\A(\s*)(.+?)(\s*)\Z/); | ||||
| 907 | return $str unless $word; | ||||
| 908 | my $plural = postprocess $word, _PL_special_adjective($word,$count) | ||||
| 909 | || $word; | ||||
| 910 | return $pre.$plural.$post; | ||||
| 911 | } | ||||
| 912 | |||||
| 913 | sub PL_eq { _PL_eq(@_, \&PL_N) || _PL_eq(@_, \&PL_V) || _PL_eq(@_, \&PL_ADJ); } | ||||
| 914 | sub PL_N_eq { _PL_eq(@_, \&PL_N); } | ||||
| 915 | sub PL_V_eq { _PL_eq(@_, \&PL_V); } | ||||
| 916 | sub PL_ADJ_eq { _PL_eq(@_, \&PL_ADJ); } | ||||
| 917 | |||||
| 918 | sub _PL_eq | ||||
| 919 | { | ||||
| 920 | my ( $word1, $word2, $PL ) = @_; | ||||
| 921 | my %classval = %classical; | ||||
| 922 | %classical = %all_classical; | ||||
| 923 | my $result = ""; | ||||
| 924 | $result = "eq" if !$result && $word1 eq $word2; | ||||
| 925 | $result = "p:s" if !$result && $word1 eq &$PL($word2); | ||||
| 926 | $result = "s:p" if !$result && &$PL($word1) eq $word2; | ||||
| 927 | %classical = (); | ||||
| 928 | $result = "p:s" if !$result && $word1 eq &$PL($word2); | ||||
| 929 | $result = "s:p" if !$result && &$PL($word1) eq $word2; | ||||
| 930 | %classical = %classval; | ||||
| 931 | |||||
| 932 | if ($PL == \&PL || $PL == \&PL_N) | ||||
| 933 | { | ||||
| 934 | $result = "p:p" | ||||
| 935 | if !$result && _PL_check_plurals_N($word1,$word2); | ||||
| 936 | $result = "p:p" | ||||
| 937 | if !$result && _PL_check_plurals_N($word2,$word1); | ||||
| 938 | } | ||||
| 939 | if ($PL == \&PL || $PL == \&PL_ADJ) | ||||
| 940 | { | ||||
| 941 | $result = "p:p" | ||||
| 942 | if !$result && _PL_check_plurals_ADJ($word1,$word2,$PL); | ||||
| 943 | } | ||||
| 944 | |||||
| 945 | return $result; | ||||
| 946 | } | ||||
| 947 | |||||
| 948 | sub _PL_reg_plurals | ||||
| 949 | { | ||||
| 950 | $_[0] =~ /($_[1])($_[2]\|\1$_[3]|$_[3]\|\1$_[2])/ | ||||
| 951 | } | ||||
| 952 | |||||
| 953 | sub _PL_check_plurals_N | ||||
| 954 | { | ||||
| 955 | my $pair = "$_[0]|$_[1]"; | ||||
| 956 | foreach ( values %PL_sb_irregular_s ) { return 1 if $_ eq $pair; } | ||||
| 957 | foreach ( values %PL_sb_irregular ) { return 1 if $_ eq $pair; } | ||||
| 958 | |||||
| 959 | return 1 if | ||||
| 960 | _PL_reg_plurals($pair, $PL_sb_U_a_ata, "as","ata") | ||||
| 961 | || _PL_reg_plurals($pair, $PL_sb_C_a_ata, "as","ata") | ||||
| 962 | || _PL_reg_plurals($pair, $PL_sb_U_is_ides, "is","ides") | ||||
| 963 | || _PL_reg_plurals($pair, $PL_sb_C_is_ides, "is","ides") | ||||
| 964 | || _PL_reg_plurals($pair, $PL_sb_C_a_ae, "s","e") | ||||
| 965 | || _PL_reg_plurals($pair, $PL_sb_C_en_ina, "ens","ina") | ||||
| 966 | || _PL_reg_plurals($pair, $PL_sb_C_um_a, "ums","a") | ||||
| 967 | || _PL_reg_plurals($pair, $PL_sb_C_us_i, "uses","i") | ||||
| 968 | || _PL_reg_plurals($pair, $PL_sb_C_on_a, "ons","a") | ||||
| 969 | || _PL_reg_plurals($pair, $PL_sb_C_o_i, "os","i") | ||||
| 970 | || _PL_reg_plurals($pair, $PL_sb_C_ex_ices, "exes","ices") | ||||
| 971 | || _PL_reg_plurals($pair, $PL_sb_C_ix_ices, "ixes","ices") | ||||
| 972 | || _PL_reg_plurals($pair, $PL_sb_C_i, "s","i") | ||||
| 973 | || _PL_reg_plurals($pair, $PL_sb_C_im, "s","im") | ||||
| 974 | |||||
| 975 | || _PL_reg_plurals($pair, '.*eau', "s","x") | ||||
| 976 | || _PL_reg_plurals($pair, '.*ieu', "s","x") | ||||
| 977 | || _PL_reg_plurals($pair, '.*tri', "xes","ces") | ||||
| 978 | || _PL_reg_plurals($pair, '.{2,}[yia]n', "xes","ges"); | ||||
| 979 | |||||
| 980 | |||||
| 981 | return 0; | ||||
| 982 | } | ||||
| 983 | |||||
| 984 | sub _PL_check_plurals_ADJ | ||||
| 985 | { | ||||
| 986 | my ( $word1a, $word2a ) = @_; | ||||
| 987 | my ( $word1b, $word2b ) = @_; | ||||
| 988 | |||||
| 989 | $word1a = '' unless $word1a =~ s/'s?$//; | ||||
| 990 | $word2a = '' unless $word2a =~ s/'s?$//; | ||||
| 991 | $word1b = '' unless $word1b =~ s/s'$//; | ||||
| 992 | $word2b = '' unless $word2b =~ s/s'$//; | ||||
| 993 | |||||
| 994 | if ($word1a) | ||||
| 995 | { | ||||
| 996 | return 1 if $word2a && ( _PL_check_plurals_N($word1a, $word2a) | ||||
| 997 | || _PL_check_plurals_N($word2a, $word1a) ); | ||||
| 998 | return 1 if $word2b && ( _PL_check_plurals_N($word1a, $word2b) | ||||
| 999 | || _PL_check_plurals_N($word2b, $word1a) ); | ||||
| 1000 | } | ||||
| 1001 | if ($word1b) | ||||
| 1002 | { | ||||
| 1003 | return 1 if $word2a && ( _PL_check_plurals_N($word1b, $word2a) | ||||
| 1004 | || _PL_check_plurals_N($word2a, $word1b) ); | ||||
| 1005 | return 1 if $word2b && ( _PL_check_plurals_N($word1b, $word2b) | ||||
| 1006 | || _PL_check_plurals_N($word2b, $word1b) ); | ||||
| 1007 | } | ||||
| 1008 | |||||
| 1009 | |||||
| 1010 | return ""; | ||||
| 1011 | } | ||||
| 1012 | |||||
| 1013 | sub _PL_noun | ||||
| 1014 | # spent 511ms (172+339) within Lingua::EN::Inflect::_PL_noun which was called 1179 times, avg 434µs/call:
# 1179 times (172ms+339ms) by Lingua::EN::Inflect::PL at line 875, avg 434µs/call | ||||
| 1015 | 1179 | 303µs | my ( $word, $count ) = @_; | ||
| 1016 | 1179 | 84µs | my $value; # UTILITY VARIABLE | ||
| 1017 | |||||
| 1018 | # DEFAULT TO PLURAL | ||||
| 1019 | |||||
| 1020 | 1179 | 259µs | $count = $persistent_count | ||
| 1021 | if !defined($count) && defined($persistent_count); | ||||
| 1022 | |||||
| 1023 | 1179 | 287µs | $count = (defined $count and $count=~/^($PL_count_one)$/io | ||
| 1024 | or defined $count and $classical{zero} | ||||
| 1025 | and $count=~/^($PL_count_zero)$/io) | ||||
| 1026 | ? 1 | ||||
| 1027 | : 2; | ||||
| 1028 | |||||
| 1029 | 1179 | 121µs | return $word if $count==1; | ||
| 1030 | |||||
| 1031 | # HANDLE USER-DEFINED NOUNS | ||||
| 1032 | |||||
| 1033 | 1179 | 1.05ms | 1179 | 1.95ms | return $value if defined($value = ud_match($word, @PL_sb_user_defined)); # spent 1.95ms making 1179 calls to Lingua::EN::Inflect::ud_match, avg 2µs/call |
| 1034 | |||||
| 1035 | |||||
| 1036 | # HANDLE EMPTY WORD, SINGULAR COUNT AND UNINFLECTED PLURALS | ||||
| 1037 | |||||
| 1038 | 1179 | 155µs | $word eq '' and return $word; | ||
| 1039 | |||||
| 1040 | 1179 | 12.8ms | 2364 | 9.56ms | $word =~ /^($PL_sb_uninflected)$/i && !exists $PL_sb_irregular{$word} && $word !~ /^($PL_sb_lese_lesen)$/i # spent 8.09ms making 1182 calls to Lingua::EN::Inflect::CORE:match, avg 7µs/call
# spent 1.47ms making 1182 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call |
| 1041 | and return $word; | ||||
| 1042 | |||||
| 1043 | 1176 | 267µs | $classical{herd} and $word =~ /^($PL_sb_uninflected_herd)$/i | ||
| 1044 | and return $word; | ||||
| 1045 | |||||
| 1046 | |||||
| 1047 | # HANDLE ISOLATED IRREGULAR PLURALS | ||||
| 1048 | |||||
| 1049 | 1176 | 10.7ms | 2352 | 5.14ms | $word =~ /^($PL_sb_irregular)$/i # spent 3.64ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call
# spent 1.50ms making 1176 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call |
| 1050 | and return ( $PL_sb_irregular{$1} || $PL_sb_irregular{lc $1} ); | ||||
| 1051 | 1176 | 33.4ms | 2353 | 28.4ms | $word =~ /(.*)\b($PL_sb_irregular)$/i # spent 27.0ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 23µs/call
# spent 1.09ms making 1176 calls to Lingua::EN::Inflect::CORE:regcomp, avg 926ns/call
# spent 271µs making 1 call to utf8::SWASHNEW |
| 1052 | and return $1 . ( $PL_sb_irregular{$2} || $PL_sb_irregular{lc $2} ); | ||||
| 1053 | |||||
| 1054 | |||||
| 1055 | # HANDLE COMPOUNDS ("Governor General", "mother-in-law", "aide-de-camp", ETC.) | ||||
| 1056 | |||||
| 1057 | 1176 | 14.0ms | 2352 | 4.35ms | $word =~ /^(?:$PL_sb_postfix_adj)$/i # spent 3.24ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call
# spent 1.11ms making 1176 calls to Lingua::EN::Inflect::CORE:regcomp, avg 946ns/call |
| 1058 | and $value = $2 | ||||
| 1059 | and return _PL_noun($1,2) | ||||
| 1060 | . $value; | ||||
| 1061 | |||||
| 1062 | 1176 | 10.5ms | 2352 | 2.90ms | $word =~ /^(?:$PL_sb_prep_dual_compound)$/i # spent 1.74ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call
# spent 1.15ms making 1176 calls to Lingua::EN::Inflect::CORE:regcomp, avg 981ns/call |
| 1063 | and $value = [$2,$3] | ||||
| 1064 | and return _PL_noun($1,2) | ||||
| 1065 | . $value->[0] | ||||
| 1066 | . _PL_noun($value->[1]); | ||||
| 1067 | |||||
| 1068 | 1176 | 11.5ms | 2352 | 3.43ms | $word =~ /^(?:$PL_sb_prep_compound)$/i # spent 2.35ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 2µs/call
# spent 1.08ms making 1176 calls to Lingua::EN::Inflect::CORE:regcomp, avg 922ns/call |
| 1069 | and $value = $2 | ||||
| 1070 | and return _PL_noun($1,2) | ||||
| 1071 | . $value; | ||||
| 1072 | |||||
| 1073 | # HANDLE PRONOUNS | ||||
| 1074 | |||||
| 1075 | 1176 | 13.5ms | 2352 | 5.44ms | $word =~ /^((?:$PL_prep)\s+)($PL_pron_acc)$/i # spent 4.01ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call
# spent 1.43ms making 1176 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call |
| 1076 | and return $1.$PL_pron_acc{lc($2)}; | ||||
| 1077 | |||||
| 1078 | 1176 | 987µs | $value = $PL_pron_nom{lc($word)} | ||
| 1079 | and return $value; | ||||
| 1080 | |||||
| 1081 | 1176 | 5.25ms | 2352 | 2.31ms | $word =~ /^($PL_pron_acc)$/i # spent 1.21ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call
# spent 1.10ms making 1176 calls to Lingua::EN::Inflect::CORE:regcomp, avg 934ns/call |
| 1082 | and return $PL_pron_acc{lc($1)}; | ||||
| 1083 | |||||
| 1084 | |||||
| 1085 | # HANDLE FAMILIES OF IRREGULAR PLURALS | ||||
| 1086 | |||||
| 1087 | 1176 | 54.0ms | 2352 | 51.2ms | $word =~ /(.*$PL_sb_U_man_mans)$/i # spent 50.1ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 43µs/call
# spent 1.04ms making 1176 calls to Lingua::EN::Inflect::CORE:regcomp, avg 881ns/call |
| 1088 | and return "$1s"; | ||||
| 1089 | 1176 | 3.42ms | 1176 | 2.05ms | $word =~ /(\S*)quy$/i # spent 2.05ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 2µs/call |
| 1090 | and return "$1quies"; | ||||
| 1091 | 1176 | 2.63ms | 1176 | 1.33ms | $word =~ /(\S*)(person)$/i and return $classical{persons}?"$1persons":"$1people"; # spent 1.33ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call |
| 1092 | 1176 | 5.86ms | 1176 | 2.08ms | $word =~ /(.*)man$/i and return "$1men"; # spent 2.08ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 2µs/call |
| 1093 | 1176 | 3.79ms | 1176 | 2.43ms | $word =~ /(.*[ml])ouse$/i and return "$1ice"; # spent 2.43ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 2µs/call |
| 1094 | 1176 | 2.84ms | 1176 | 1.57ms | $word =~ /(.*)goose$/i and return "$1geese"; # spent 1.57ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call |
| 1095 | 1176 | 4.43ms | 1176 | 3.13ms | $word =~ /(.*)tooth$/i and return "$1teeth"; # spent 3.13ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 1096 | 1176 | 4.76ms | 1176 | 3.44ms | $word =~ /(.*)foot$/i and return "$1feet"; # spent 3.44ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 1097 | |||||
| 1098 | # HANDLE UNASSIMILATED IMPORTS | ||||
| 1099 | |||||
| 1100 | 1176 | 3.08ms | 1176 | 1.81ms | $word =~ /(.*)ceps$/i and return $word; # spent 1.81ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 2µs/call |
| 1101 | 1176 | 2.92ms | 1176 | 1.62ms | $word =~ /(.*)zoon$/i and return "$1zoa"; # spent 1.62ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call |
| 1102 | 1176 | 8.01ms | 1176 | 4.06ms | $word =~ /(.*[csx])is$/i and return "$1es"; # spent 4.06ms making 1176 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 1103 | 1175 | 5.40ms | 2350 | 2.69ms | $word =~ /(.*$PL_sb_U_a_ata)a$/i and return "$1ata"; # spent 1.44ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call
# spent 1.25ms making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call |
| 1104 | 1175 | 6.34ms | 2350 | 3.58ms | $word =~ /(.*$PL_sb_U_is_ides)is$/i and return "$1ides"; # spent 2.89ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 2µs/call
# spent 694µs making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 590ns/call |
| 1105 | 1175 | 13.7ms | 2350 | 8.10ms | $word =~ /(.*$PL_sb_U_ch_chs)ch$/i and return "$1chs"; # spent 7.11ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 6µs/call
# spent 985µs making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 838ns/call |
| 1106 | 1175 | 10.5ms | 2350 | 7.80ms | $word =~ /(.*$PL_sb_U_ex_ices)ex$/i and return "$1ices"; # spent 6.85ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 6µs/call
# spent 957µs making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 814ns/call |
| 1107 | 1175 | 8.98ms | 2350 | 6.24ms | $word =~ /(.*$PL_sb_U_ix_ices)ix$/i and return "$1ices"; # spent 5.29ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 5µs/call
# spent 944µs making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 803ns/call |
| 1108 | 1175 | 29.1ms | 2350 | 26.3ms | $word =~ /(.*$PL_sb_U_um_a)um$/i and return "$1a"; # spent 25.3ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 22µs/call
# spent 993µs making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 845ns/call |
| 1109 | 1175 | 29.2ms | 2350 | 23.4ms | $word =~ /(.*$PL_sb_U_us_i)us$/i and return "$1i"; # spent 22.2ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 19µs/call
# spent 1.23ms making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call |
| 1110 | 1175 | 16.9ms | 2350 | 14.2ms | $word =~ /(.*$PL_sb_U_on_a)on$/i and return "$1a"; # spent 13.2ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 11µs/call
# spent 978µs making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 833ns/call |
| 1111 | 1175 | 21.2ms | 2350 | 10.9ms | $word =~ /(.*$PL_sb_U_a_ae)$/i and return "$1e"; # spent 9.97ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 8µs/call
# spent 925µs making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 787ns/call |
| 1112 | 1175 | 9.91ms | 2350 | 7.19ms | $word =~ /(.*$PL_sb_lese_lesen)$/i and return "$1n"; # spent 6.20ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 5µs/call
# spent 993µs making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 845ns/call |
| 1113 | |||||
| 1114 | # HANDLE INCOMPLETELY ASSIMILATED IMPORTS | ||||
| 1115 | |||||
| 1116 | 1175 | 247µs | if ($classical{ancient}) | ||
| 1117 | { | ||||
| 1118 | $word =~ /(.*)trix$/i and return "$1trices"; | ||||
| 1119 | $word =~ /(.*)eau$/i and return "$1eaux"; | ||||
| 1120 | $word =~ /(.*)ieu$/i and return "$1ieux"; | ||||
| 1121 | $word =~ /(.{2,}[yia])nx$/i and return "$1nges"; | ||||
| 1122 | $word =~ /(.*$PL_sb_C_en_ina)en$/i and return "$1ina"; | ||||
| 1123 | $word =~ /(.*$PL_sb_C_ex_ices)ex$/i and return "$1ices"; | ||||
| 1124 | $word =~ /(.*$PL_sb_C_ix_ices)ix$/i and return "$1ices"; | ||||
| 1125 | $word =~ /(.*$PL_sb_C_um_a)um$/i and return "$1a"; | ||||
| 1126 | $word =~ /(.*$PL_sb_C_us_i)us$/i and return "$1i"; | ||||
| 1127 | $word =~ /(.*$PL_sb_C_us_us)$/i and return "$1"; | ||||
| 1128 | $word =~ /(.*$PL_sb_C_a_ae)$/i and return "$1e"; | ||||
| 1129 | $word =~ /(.*$PL_sb_C_a_ata)a$/i and return "$1ata"; | ||||
| 1130 | $word =~ /(.*$PL_sb_C_is_ides)is$/i and return "$1ides"; | ||||
| 1131 | $word =~ /(.*$PL_sb_C_o_i)o$/i and return "$1i"; | ||||
| 1132 | $word =~ /(.*$PL_sb_C_on_a)on$/i and return "$1a"; | ||||
| 1133 | $word =~ /$PL_sb_C_im$/i and return "${word}im"; | ||||
| 1134 | $word =~ /$PL_sb_C_i$/i and return "${word}i"; | ||||
| 1135 | } | ||||
| 1136 | |||||
| 1137 | |||||
| 1138 | # HANDLE SINGULAR NOUNS ENDING IN ...s OR OTHER SILIBANTS | ||||
| 1139 | |||||
| 1140 | 1175 | 11.1ms | 2350 | 5.48ms | $word =~ /^($PL_sb_singular_s)$/i and return "$1es"; # spent 4.27ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 4µs/call
# spent 1.21ms making 1175 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call |
| 1141 | 1158 | 1.96ms | 1158 | 476µs | $word =~ /^([A-Z].*s)$/ and $classical{names} and return "$1es"; # spent 476µs making 1158 calls to Lingua::EN::Inflect::CORE:match, avg 411ns/call |
| 1142 | 1131 | 4.56ms | 2262 | 1.81ms | $word =~ /^($PL_sb_z_zes)$/i and return "$1es"; # spent 1.03ms making 1131 calls to Lingua::EN::Inflect::CORE:regcomp, avg 908ns/call
# spent 783µs making 1131 calls to Lingua::EN::Inflect::CORE:match, avg 692ns/call |
| 1143 | 1131 | 8.21ms | 1131 | 1.30ms | $word =~ /^(.*[^z])(z)$/i and return "$1zzes"; # spent 1.30ms making 1131 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call |
| 1144 | 1129 | 4.70ms | 1129 | 3.02ms | $word =~ /^(.*)([cs]h|x|zz|ss)$/i and return "$1$2es"; # spent 3.02ms making 1129 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 1145 | # $word =~ /(.*)(us)$/i and return "$1$2es"; | ||||
| 1146 | |||||
| 1147 | # HANDLE ...f -> ...ves | ||||
| 1148 | |||||
| 1149 | 1086 | 8.96ms | 1086 | 3.16ms | $word =~ /(.*[eao])lf$/i and return "$1lves"; # spent 3.16ms making 1086 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 1150 | 1086 | 4.84ms | 1086 | 3.61ms | $word =~ /(.*[^d])eaf$/i and return "$1eaves"; # spent 3.61ms making 1086 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 1151 | 1086 | 3.76ms | 1086 | 2.57ms | $word =~ /(.*[nlw])ife$/i and return "$1ives"; # spent 2.57ms making 1086 calls to Lingua::EN::Inflect::CORE:match, avg 2µs/call |
| 1152 | 1086 | 4.88ms | 1086 | 3.63ms | $word =~ /(.*)arf$/i and return "$1arves"; # spent 3.63ms making 1086 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 1153 | |||||
| 1154 | # HANDLE ...y | ||||
| 1155 | |||||
| 1156 | 1086 | 4.59ms | 1086 | 3.33ms | $word =~ /(.*[aeiou])y$/i and return "$1ys"; # spent 3.33ms making 1086 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 1157 | 1083 | 3.99ms | 1083 | 407µs | $word =~ /([A-Z].*y)$/ and $classical{names} and return "$1s"; # spent 407µs making 1083 calls to Lingua::EN::Inflect::CORE:match, avg 376ns/call |
| 1158 | 1080 | 5.48ms | 1080 | 3.99ms | $word =~ /(.*)y$/i and return "$1ies"; # spent 3.99ms making 1080 calls to Lingua::EN::Inflect::CORE:match, avg 4µs/call |
| 1159 | |||||
| 1160 | # HANDLE ...o | ||||
| 1161 | |||||
| 1162 | 1050 | 62.0ms | 2100 | 56.8ms | $word =~ /$PL_sb_U_o_os$/i and return "${word}s"; # spent 55.5ms making 1050 calls to Lingua::EN::Inflect::CORE:match, avg 53µs/call
# spent 1.30ms making 1050 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call |
| 1163 | 1047 | 1.96ms | 1047 | 691µs | $word =~ /[aeiou]o$/i and return "${word}s"; # spent 691µs making 1047 calls to Lingua::EN::Inflect::CORE:match, avg 660ns/call |
| 1164 | 1043 | 1.83ms | 1043 | 538µs | $word =~ /o$/i and return "${word}es"; # spent 538µs making 1043 calls to Lingua::EN::Inflect::CORE:match, avg 516ns/call |
| 1165 | |||||
| 1166 | |||||
| 1167 | # OTHERWISE JUST ADD ...s | ||||
| 1168 | |||||
| 1169 | 1030 | 9.34ms | return "${word}s"; | ||
| 1170 | } | ||||
| 1171 | |||||
| 1172 | |||||
| 1173 | sub _PL_special_verb | ||||
| 1174 | # spent 98.4ms (69.5+28.9) within Lingua::EN::Inflect::_PL_special_verb which was called 1220 times, avg 81µs/call:
# 1220 times (69.5ms+28.9ms) by Lingua::EN::Inflect::PL at line 875, avg 81µs/call | ||||
| 1175 | 1220 | 283µs | my ( $word, $count ) = @_; | ||
| 1176 | 1220 | 246µs | $count = $persistent_count | ||
| 1177 | if !defined($count) && defined($persistent_count); | ||||
| 1178 | 1220 | 295µs | $count = (defined $count and $count=~/^($PL_count_one)$/io or | ||
| 1179 | defined $count and $classical{zero} and $count=~/^($PL_count_zero)$/io) ? 1 | ||||
| 1180 | : 2; | ||||
| 1181 | |||||
| 1182 | 1220 | 5.66ms | 1221 | 1.02ms | return undef if $count=~/^($PL_count_one)$/io; # spent 1.01ms making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 827ns/call
# spent 7µs making 1 call to Lingua::EN::Inflect::CORE:regcomp |
| 1183 | |||||
| 1184 | 1220 | 24µs | my $value; # UTILITY VARIABLE | ||
| 1185 | |||||
| 1186 | # HANDLE USER-DEFINED VERBS | ||||
| 1187 | |||||
| 1188 | 1220 | 1.30ms | 1220 | 2.23ms | return $value if defined($value = ud_match($word, @PL_v_user_defined)); # spent 2.23ms making 1220 calls to Lingua::EN::Inflect::ud_match, avg 2µs/call |
| 1189 | |||||
| 1190 | # HANDLE IRREGULAR PRESENT TENSE (SIMPLE AND COMPOUND) | ||||
| 1191 | |||||
| 1192 | 1220 | 9.17ms | 2440 | 2.82ms | $word =~ /^($PL_v_irregular_pres)((\s.*)?)$/i # spent 1.56ms making 1220 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call
# spent 1.25ms making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call |
| 1193 | and return $PL_v_irregular_pres{lc $1}.$2; | ||||
| 1194 | |||||
| 1195 | # HANDLE IRREGULAR FUTURE, PRETERITE AND PERFECT TENSES | ||||
| 1196 | |||||
| 1197 | 1220 | 19.7ms | 2440 | 2.45ms | $word =~ /^($PL_v_irregular_non_pres)((\s.*)?)$/i # spent 1.37ms making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call
# spent 1.09ms making 1220 calls to Lingua::EN::Inflect::CORE:regcomp, avg 889ns/call |
| 1198 | and return $word; | ||||
| 1199 | |||||
| 1200 | # HANDLE PRESENT NEGATIONS (SIMPLE AND COMPOUND) | ||||
| 1201 | |||||
| 1202 | 1220 | 5.14ms | 2440 | 2.16ms | $word =~ /^($PL_v_irregular_pres)(n't(\s.*)?)$/i # spent 1.24ms making 1220 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call
# spent 928µs making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 761ns/call |
| 1203 | and return $PL_v_irregular_pres{lc $1}.$2; | ||||
| 1204 | |||||
| 1205 | 1220 | 2.65ms | 1220 | 1.20ms | $word =~ /^\S+n't\b/i # spent 1.20ms making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 982ns/call |
| 1206 | and return $word; | ||||
| 1207 | |||||
| 1208 | # HANDLE SPECIAL CASES | ||||
| 1209 | |||||
| 1210 | 1220 | 8.05ms | 2440 | 4.91ms | $word =~ /^($PL_v_special_s)$/ and return undef; # spent 3.56ms making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call
# spent 1.36ms making 1220 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call |
| 1211 | 1175 | 4.16ms | 1175 | 410µs | $word =~ /\s/ and return undef; # spent 410µs making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 349ns/call |
| 1212 | 1175 | 1.63ms | 1175 | 352µs | $word =~ /^quizzes$/i and return "quiz"; # spent 352µs making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 299ns/call |
| 1213 | |||||
| 1214 | # HANDLE STANDARD 3RD PERSON (CHOP THE ...(e)s OFF SINGLE WORDS) | ||||
| 1215 | |||||
| 1216 | 1175 | 4.68ms | 1175 | 3.23ms | $word =~ /^(.*)([cs]h|[x]|zz|ss)es$/i and return "$1$2"; # spent 3.23ms making 1175 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call |
| 1217 | |||||
| 1218 | 1174 | 2.34ms | 1174 | 964µs | $word =~ /^(..+)ies$/i and return "$1y"; # spent 964µs making 1174 calls to Lingua::EN::Inflect::CORE:match, avg 821ns/call |
| 1219 | |||||
| 1220 | 1173 | 10.8ms | 2346 | 5.18ms | $word =~ /($PL_v_oes_oe)$/ and return substr($1,0,-1); # spent 3.72ms making 1173 calls to Lingua::EN::Inflect::CORE:match, avg 3µs/call
# spent 1.46ms making 1173 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call |
| 1221 | 1173 | 9.13ms | 1173 | 738µs | $word =~ /^(.+)oes$/i and return "$1o"; # spent 738µs making 1173 calls to Lingua::EN::Inflect::CORE:match, avg 629ns/call |
| 1222 | |||||
| 1223 | 1173 | 2.82ms | 1173 | 1.28ms | $word =~ /^(.*[^s])s$/i and return $1; # spent 1.28ms making 1173 calls to Lingua::EN::Inflect::CORE:match, avg 1µs/call |
| 1224 | |||||
| 1225 | # OTHERWISE, A REGULAR VERB (HANDLE ELSEWHERE) | ||||
| 1226 | |||||
| 1227 | 1134 | 3.26ms | return undef; | ||
| 1228 | } | ||||
| 1229 | |||||
| 1230 | sub _PL_general_verb | ||||
| 1231 | { | ||||
| 1232 | my ( $word, $count ) = @_; | ||||
| 1233 | $count = $persistent_count | ||||
| 1234 | if !defined($count) && defined($persistent_count); | ||||
| 1235 | $count = (defined $count and $count=~/^($PL_count_one)$/io or | ||||
| 1236 | defined $count and $classical{zero} and $count=~/^($PL_count_zero)$/io) ? 1 | ||||
| 1237 | : 2; | ||||
| 1238 | |||||
| 1239 | return $word if $count=~/^($PL_count_one)$/io; | ||||
| 1240 | |||||
| 1241 | # HANDLE AMBIGUOUS PRESENT TENSES (SIMPLE AND COMPOUND) | ||||
| 1242 | |||||
| 1243 | $word =~ /^($PL_v_ambiguous_pres)((\s.*)?)$/i | ||||
| 1244 | and return $PL_v_ambiguous_pres{lc $1}.$2; | ||||
| 1245 | |||||
| 1246 | # HANDLE AMBIGUOUS PRETERITE AND PERFECT TENSES | ||||
| 1247 | |||||
| 1248 | $word =~ /^($PL_v_ambiguous_non_pres)((\s.*)?)$/i | ||||
| 1249 | and return $word; | ||||
| 1250 | |||||
| 1251 | # OTHERWISE, 1st OR 2ND PERSON IS UNINFLECTED | ||||
| 1252 | |||||
| 1253 | return $word; | ||||
| 1254 | |||||
| 1255 | } | ||||
| 1256 | |||||
| 1257 | sub _PL_special_adjective | ||||
| 1258 | # spent 30.3ms (21.0+9.32) within Lingua::EN::Inflect::_PL_special_adjective which was called 1220 times, avg 25µs/call:
# 1220 times (21.0ms+9.32ms) by Lingua::EN::Inflect::PL at line 875, avg 25µs/call | ||||
| 1259 | 1220 | 214µs | my ( $word, $count ) = @_; | ||
| 1260 | 1220 | 302µs | $count = $persistent_count | ||
| 1261 | if !defined($count) && defined($persistent_count); | ||||
| 1262 | 1220 | 285µs | $count = (defined $count and $count=~/^($PL_count_one)$/io or | ||
| 1263 | defined $count and $classical{zero} and $count=~/^($PL_count_zero)$/io) ? 1 | ||||
| 1264 | : 2; | ||||
| 1265 | |||||
| 1266 | 1220 | 2.97ms | 1221 | 1.15ms | return $word if $count=~/^($PL_count_one)$/io; # spent 1.13ms making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 924ns/call
# spent 18µs making 1 call to Lingua::EN::Inflect::CORE:regcomp |
| 1267 | |||||
| 1268 | |||||
| 1269 | # HANDLE USER-DEFINED ADJECTIVES | ||||
| 1270 | |||||
| 1271 | 1220 | 19µs | my $value; | ||
| 1272 | 1220 | 1.35ms | 1220 | 2.48ms | return $value if defined($value = ud_match($word, @PL_adj_user_defined)); # spent 2.48ms making 1220 calls to Lingua::EN::Inflect::ud_match, avg 2µs/call |
| 1273 | |||||
| 1274 | # HANDLE KNOWN CASES | ||||
| 1275 | |||||
| 1276 | 1220 | 8.47ms | 2440 | 2.54ms | $word =~ /^($PL_adj_special)$/i # spent 1.50ms making 1220 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call
# spent 1.04ms making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 850ns/call |
| 1277 | and return $PL_adj_special{lc $1}; | ||||
| 1278 | |||||
| 1279 | # HANDLE POSSESSIVES | ||||
| 1280 | |||||
| 1281 | 1220 | 5.41ms | 2440 | 2.30ms | $word =~ /^($PL_adj_poss)$/i # spent 1.36ms making 1220 calls to Lingua::EN::Inflect::CORE:regcomp, avg 1µs/call
# spent 942µs making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 772ns/call |
| 1282 | and return $PL_adj_poss{lc $1}; | ||||
| 1283 | |||||
| 1284 | 1220 | 4.66ms | 1220 | 848µs | $word =~ /^(.*)'s?$/ and do { my $pl = PL_N($1); # spent 848µs making 1220 calls to Lingua::EN::Inflect::CORE:match, avg 695ns/call |
| 1285 | return "$pl'" . ($pl =~ m/s$/ ? "" : "s"); | ||||
| 1286 | }; | ||||
| 1287 | |||||
| 1288 | # OTHERWISE, NO IDEA | ||||
| 1289 | |||||
| 1290 | 1220 | 2.45ms | return undef; | ||
| 1291 | |||||
| 1292 | } | ||||
| 1293 | |||||
| 1294 | |||||
| 1295 | # 2. INDEFINITE ARTICLES | ||||
| 1296 | |||||
| 1297 | # THIS PATTERN MATCHES STRINGS OF CAPITALS STARTING WITH A "VOWEL-SOUND" | ||||
| 1298 | # CONSONANT FOLLOWED BY ANOTHER CONSONANT, AND WHICH ARE NOT LIKELY | ||||
| 1299 | # TO BE REAL WORDS (OH, ALL RIGHT THEN, IT'S JUST MAGIC!) | ||||
| 1300 | |||||
| 1301 | 1 | 400ns | my $A_abbrev = q{ | ||
| 1302 | (?! FJO | [HLMNS]Y. | RY[EO] | SQU | ||||
| 1303 | | ( F[LR]? | [HL] | MN? | N | RH? | S[CHKLMNPTVW]? | X(YL)?) [AEIOU]) | ||||
| 1304 | [FHLMNRSX][A-Z] | ||||
| 1305 | }; | ||||
| 1306 | |||||
| 1307 | # THIS PATTERN CODES THE BEGINNINGS OF ALL ENGLISH WORDS BEGINING WITH A | ||||
| 1308 | # 'y' FOLLOWED BY A CONSONANT. ANY OTHER Y-CONSONANT PREFIX THEREFORE | ||||
| 1309 | # IMPLIES AN ABBREVIATION. | ||||
| 1310 | |||||
| 1311 | 1 | 200ns | my $A_y_cons = 'y(b[lor]|cl[ea]|fere|gg|p[ios]|rou|tt)'; | ||
| 1312 | |||||
| 1313 | # EXCEPTIONS TO EXCEPTIONS | ||||
| 1314 | |||||
| 1315 | 1 | 2µs | 1 | 1µs | my $A_explicit_an = enclose join '|', # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 1316 | ( | ||||
| 1317 | "euler", | ||||
| 1318 | "hour(?!i)", "heir", "honest", "hono", | ||||
| 1319 | ); | ||||
| 1320 | |||||
| 1321 | 1 | 1µs | 1 | 1µs | my $A_ordinal_an = enclose join '|', # spent 1µs making 1 call to Lingua::EN::Inflect::enclose |
| 1322 | ( | ||||
| 1323 | "[aefhilmnorsx]-?th", | ||||
| 1324 | ); | ||||
| 1325 | |||||
| 1326 | 1 | 1µs | 1 | 900ns | my $A_ordinal_a = enclose join '|', # spent 900ns making 1 call to Lingua::EN::Inflect::enclose |
| 1327 | ( | ||||
| 1328 | "[bcdgjkpqtuvwyz]-?th", | ||||
| 1329 | ); | ||||
| 1330 | |||||
| 1331 | sub A { | ||||
| 1332 | my ($str, $count) = @_; | ||||
| 1333 | my ($pre, $word, $post) = ( $str =~ m/\A(\s*)(?:an?\s+)?(.+?)(\s*)\Z/i ); | ||||
| 1334 | return $str unless $word; | ||||
| 1335 | my $result = _indef_article($word,$count); | ||||
| 1336 | return $pre.$result.$post; | ||||
| 1337 | } | ||||
| 1338 | |||||
| 1339 | sub AN { goto &A } | ||||
| 1340 | |||||
| 1341 | sub _indef_article { | ||||
| 1342 | my ( $word, $count ) = @_; | ||||
| 1343 | |||||
| 1344 | $count = $persistent_count | ||||
| 1345 | if !defined($count) && defined($persistent_count); | ||||
| 1346 | |||||
| 1347 | return "$count $word" | ||||
| 1348 | if defined $count && $count!~/^($PL_count_one)$/io; | ||||
| 1349 | |||||
| 1350 | # HANDLE USER-DEFINED VARIANTS | ||||
| 1351 | |||||
| 1352 | my $value; | ||||
| 1353 | return "$value $word" | ||||
| 1354 | if defined($value = ud_match($word, @A_a_user_defined)); | ||||
| 1355 | |||||
| 1356 | # HANDLE ORDINAL FORMS | ||||
| 1357 | |||||
| 1358 | $word =~ /^($A_ordinal_a)/i and return "a $word"; | ||||
| 1359 | $word =~ /^($A_ordinal_an)/i and return "an $word"; | ||||
| 1360 | |||||
| 1361 | # HANDLE SPECIAL CASES | ||||
| 1362 | |||||
| 1363 | $word =~ /^($A_explicit_an)/i and return "an $word"; | ||||
| 1364 | $word =~ /^[aefhilmnorsx]$/i and return "an $word"; | ||||
| 1365 | $word =~ /^[bcdgjkpqtuvwyz]$/i and return "a $word"; | ||||
| 1366 | |||||
| 1367 | |||||
| 1368 | # HANDLE ABBREVIATIONS | ||||
| 1369 | |||||
| 1370 | $word =~ /^($A_abbrev)/ox and return "an $word"; | ||||
| 1371 | $word =~ /^[aefhilmnorsx][.-]/i and return "an $word"; | ||||
| 1372 | $word =~ /^[a-z][.-]/i and return "a $word"; | ||||
| 1373 | |||||
| 1374 | # HANDLE CONSONANTS | ||||
| 1375 | |||||
| 1376 | $word =~ /^[^aeiouy]/i and return "a $word"; | ||||
| 1377 | |||||
| 1378 | # HANDLE SPECIAL VOWEL-FORMS | ||||
| 1379 | |||||
| 1380 | $word =~ /^e[uw]/i and return "a $word"; | ||||
| 1381 | $word =~ /^onc?e\b/i and return "a $word"; | ||||
| 1382 | $word =~ /^uni([^nmd]|mo)/i and return "a $word"; | ||||
| 1383 | $word =~ /^ut[th]/i and return "an $word"; | ||||
| 1384 | $word =~ /^u[bcfhjkqrst][aeiou]/i and return "a $word"; | ||||
| 1385 | |||||
| 1386 | # HANDLE SPECIAL CAPITALS | ||||
| 1387 | |||||
| 1388 | $word =~ /^U[NK][AIEO]?/ and return "a $word"; | ||||
| 1389 | |||||
| 1390 | # HANDLE VOWELS | ||||
| 1391 | |||||
| 1392 | $word =~ /^[aeiou]/i and return "an $word"; | ||||
| 1393 | |||||
| 1394 | # HANDLE y... (BEFORE CERTAIN CONSONANTS IMPLIES (UNNATURALIZED) "i.." SOUND) | ||||
| 1395 | |||||
| 1396 | $word =~ /^($A_y_cons)/io and return "an $word"; | ||||
| 1397 | |||||
| 1398 | # OTHERWISE, GUESS "a" | ||||
| 1399 | return "a $word"; | ||||
| 1400 | } | ||||
| 1401 | |||||
| 1402 | # 2. TRANSLATE ZERO-QUANTIFIED $word TO "no PL($word)" | ||||
| 1403 | |||||
| 1404 | sub NO | ||||
| 1405 | { | ||||
| 1406 | my ($str, $count, $opt_ref) = @_; | ||||
| 1407 | my ($pre, $word, $post) = ($str =~ m/\A(\s*)(.+?)(\s*)\Z/); | ||||
| 1408 | |||||
| 1409 | $count = $persistent_count | ||||
| 1410 | if !defined($count) && defined($persistent_count); | ||||
| 1411 | $count = 0 unless $count; | ||||
| 1412 | |||||
| 1413 | if ($count =~ /^$PL_count_zero$/) { | ||||
| 1414 | return "${pre}no ". PL($word,0) . $post ; | ||||
| 1415 | } | ||||
| 1416 | |||||
| 1417 | $count = defined $opt_ref->{words_below} && $count < $opt_ref->{words_below} | ||||
| 1418 | ? NUMWORDS($count) | ||||
| 1419 | : $count; | ||||
| 1420 | |||||
| 1421 | if (defined $opt_ref->{comma} || defined $opt_ref->{comma_every}) { | ||||
| 1422 | $opt_ref->{comma_every} = 3 if !defined $opt_ref->{comma_every}; | ||||
| 1423 | $opt_ref->{comma} = ',' if !defined $opt_ref->{comma} | ||||
| 1424 | || $opt_ref->{comma} =~ /^\d+$/; | ||||
| 1425 | |||||
| 1426 | $count = _commify($count, @{$opt_ref}{'comma','comma_every'}); | ||||
| 1427 | } | ||||
| 1428 | |||||
| 1429 | return "$pre$count " . PL($word,$count) . $post | ||||
| 1430 | } | ||||
| 1431 | |||||
| 1432 | sub _commify { | ||||
| 1433 | my ($number, $comma, $every) = @_; | ||||
| 1434 | return if !defined $comma; | ||||
| 1435 | return if !defined $comma; | ||||
| 1436 | $number =~ s{(?:(?<=^)|(?<=^-))(\d\d{$every,})} | ||||
| 1437 | { my $n = $1; | ||||
| 1438 | $n=~s/(?<=.)(?=(?:.{$every})+$)/$comma/g; | ||||
| 1439 | $n; | ||||
| 1440 | }e; | ||||
| 1441 | return $number; | ||||
| 1442 | } | ||||
| 1443 | |||||
| 1444 | # PARTICIPLES | ||||
| 1445 | |||||
| 1446 | sub PART_PRES | ||||
| 1447 | { | ||||
| 1448 | local $_ = PL_V(shift,2); | ||||
| 1449 | s/ie$/y/ | ||||
| 1450 | or s/ue$/u/ | ||||
| 1451 | or s/([auy])e$/$1/ | ||||
| 1452 | or s/ski$/ski/ | ||||
| 1453 | or s/[^b]i$// | ||||
| 1454 | or s/^(are|were)$/be/ | ||||
| 1455 | or s/^(had)$/hav/ | ||||
| 1456 | or s/(hoe)$/$1/ | ||||
| 1457 | or s/([^e])e$/$1/ | ||||
| 1458 | or m/er$/ | ||||
| 1459 | or s/([^aeiou][aeiouy]([bdgmnprst]))$/$1$2/; | ||||
| 1460 | return "${_}ing"; | ||||
| 1461 | } | ||||
| 1462 | |||||
| - - | |||||
| 1465 | # NUMERICAL INFLECTIONS | ||||
| 1466 | |||||
| 1467 | 1 | 7µs | my %nth = | ||
| 1468 | ( | ||||
| 1469 | 0 => 'th', | ||||
| 1470 | 1 => 'st', | ||||
| 1471 | 2 => 'nd', | ||||
| 1472 | 3 => 'rd', | ||||
| 1473 | 4 => 'th', | ||||
| 1474 | 5 => 'th', | ||||
| 1475 | 6 => 'th', | ||||
| 1476 | 7 => 'th', | ||||
| 1477 | 8 => 'th', | ||||
| 1478 | 9 => 'th', | ||||
| 1479 | 11 => 'th', | ||||
| 1480 | 12 => 'th', | ||||
| 1481 | 13 => 'th', | ||||
| 1482 | ); | ||||
| 1483 | |||||
| 1484 | |||||
| 1485 | 1 | 100ns | my %ordinal; | ||
| 1486 | 1 | 4µs | @ordinal{qw(ty one two three five eight nine twelve )}= | ||
| 1487 | qw(tieth first second third fifth eighth ninth twelfth); | ||||
| 1488 | |||||
| 1489 | 1 | 2µs | my $ordinal_suff = join '|', keys %ordinal, ""; | ||
| 1490 | |||||
| 1491 | 1 | 500ns | $ordinal{""} = 'th'; | ||
| 1492 | |||||
| 1493 | sub ORD($) | ||||
| 1494 | { | ||||
| 1495 | my $num = shift; | ||||
| 1496 | if ($num =~ /\d/) { | ||||
| 1497 | return $num . ($nth{$num%100} || $nth{$num%10}); | ||||
| 1498 | } | ||||
| 1499 | else { | ||||
| 1500 | $num =~ s/($ordinal_suff)\Z/$ordinal{$1}/; | ||||
| 1501 | return $num; | ||||
| 1502 | } | ||||
| 1503 | } | ||||
| 1504 | |||||
| 1505 | |||||
| 1506 | 1 | 2µs | my %default_args = | ||
| 1507 | ( | ||||
| 1508 | 'group' => 0, | ||||
| 1509 | 'comma' => ',', | ||||
| 1510 | 'and' => 'and', | ||||
| 1511 | 'zero' => 'zero', | ||||
| 1512 | 'one' => 'one', | ||||
| 1513 | 'decimal' => 'point', | ||||
| 1514 | ); | ||||
| 1515 | |||||
| 1516 | 1 | 4µs | my @unit = ('',qw(one two three four five six seven eight nine)); | ||
| 1517 | 1 | 1µs | my @teen = qw(ten eleven twelve thirteen fourteen | ||
| 1518 | fifteen sixteen seventeen eighteen nineteen); | ||||
| 1519 | 1 | 1µs | my @ten = ('','',qw(twenty thirty forty fifty sixty seventy eighty ninety)); | ||
| 1520 | 25 | 39µs | 12 | 12µs | my @mill = map { (my $val=$_) =~ s/_/illion/; " $val" } # spent 12µs making 12 calls to Lingua::EN::Inflect::CORE:subst, avg 975ns/call |
| 1521 | ('',qw(thousand m_ b_ tr_ quadr_ quint_ sext_ sept_ oct_ non_ dec_)); | ||||
| 1522 | |||||
| 1523 | |||||
| 1524 | sub mill { my $ind = $_[0]||0; | ||||
| 1525 | die "Number out of range\n" if $ind > $#mill; | ||||
| 1526 | return $ind<@mill ? $mill[$ind] : ' ???illion'; } | ||||
| 1527 | |||||
| 1528 | sub unit { return $unit[$_[0]]. mill($_[1]); } | ||||
| 1529 | |||||
| 1530 | sub ten | ||||
| 1531 | { | ||||
| 1532 | return $ten[$_[0]] . ($_[0]&&$_[1]?'-':'') . $unit[$_[1]] . mill($_[2]) | ||||
| 1533 | if $_[0] ne '1'; | ||||
| 1534 | return $teen[$_[1]]. $mill[$_[2]||0]; | ||||
| 1535 | } | ||||
| 1536 | |||||
| 1537 | sub hund | ||||
| 1538 | { | ||||
| 1539 | return unit($_[0]) . " hundred" . ($_[1] || $_[2] ? " $_[4] " : '') | ||||
| 1540 | . ten($_[1],$_[2]) . mill($_[3]) . ', ' if $_[0]; | ||||
| 1541 | return ten($_[1],$_[2]) . mill($_[3]) . ', ' if $_[1] || $_[2]; | ||||
| 1542 | return ''; | ||||
| 1543 | } | ||||
| 1544 | |||||
| 1545 | |||||
| 1546 | sub enword | ||||
| 1547 | { | ||||
| 1548 | my ($num,$group,$zero,$one,$comma,$and) = @_; | ||||
| 1549 | |||||
| 1550 | if ($group==1) | ||||
| 1551 | { | ||||
| 1552 | $num =~ s/(\d)/ ($1==1 ? " $one" : $1 ? unit($1) :" $zero")."$comma " /eg; | ||||
| 1553 | } | ||||
| 1554 | elsif ($group==2) | ||||
| 1555 | { | ||||
| 1556 | $num =~ s/(\d)(\d)/ ($1 ? ten($1,$2) : $2 ? " $zero " . unit($2) : " $zero $zero") . "$comma " /eg; | ||||
| 1557 | $num =~ s/(\d)/ ($1 ? unit($1) :" $zero")."$comma " /e; | ||||
| 1558 | } | ||||
| 1559 | elsif ($group==3) | ||||
| 1560 | { | ||||
| 1561 | $num =~ s/(\d)(\d)(\d)/ ($1==1 ? " $one" : $1 ? unit($1) :" $zero")." ".($2 ? ten($2,$3) : $3 ? " $zero " . unit($3) : " $zero $zero") . "$comma " /eg; | ||||
| 1562 | $num =~ s/(\d)(\d)/ ($1 ? ten($1,$2) : $2 ? " $zero " . unit($2) : " $zero $zero") . "$comma " /e; | ||||
| 1563 | $num =~ s/(\d)/ ($1==1 ? " $one" : $1 ? unit($1) :" $zero")."$comma " /e; | ||||
| 1564 | } | ||||
| 1565 | elsif ($num+0==0) { | ||||
| 1566 | $num = $zero; | ||||
| 1567 | } | ||||
| 1568 | elsif ($num+0==1) { | ||||
| 1569 | $num = $one; | ||||
| 1570 | } | ||||
| 1571 | else { | ||||
| 1572 | $num =~ s/\A\s*0+//; | ||||
| 1573 | my $mill = 0; | ||||
| 1574 | 1 while $num =~ s/(\d)(\d)(\d)(?=\D*\Z)/ hund($1,$2,$3,$mill++,$and) /e; | ||||
| 1575 | $num =~ s/(\d)(\d)(?=\D*\Z)/ ten($1,$2,$mill)."$comma " /e; | ||||
| 1576 | $num =~ s/(\d)(?=\D*\Z)/ unit($1,$mill) . "$comma "/e; | ||||
| 1577 | } | ||||
| 1578 | return $num; | ||||
| 1579 | } | ||||
| 1580 | |||||
| 1581 | sub NUMWORDS | ||||
| 1582 | { | ||||
| 1583 | my $num = shift; | ||||
| 1584 | |||||
| 1585 | if (@_ % 2 and require Carp) { | ||||
| 1586 | die "Missing value in option list (odd number of option args) at" | ||||
| 1587 | . join ' line ', (caller)[1,2]; | ||||
| 1588 | } | ||||
| 1589 | |||||
| 1590 | my %arg = ( %default_args, @_ ); | ||||
| 1591 | my $group = $arg{group}; | ||||
| 1592 | |||||
| 1593 | # Handle "stylistic" conversions (up to a given threshold)... | ||||
| 1594 | if (exists $arg{threshold} && $num > $arg{threshold}) { | ||||
| 1595 | my ($whole, $frac) = split /[.]/, $num; | ||||
| 1596 | while ($arg{comma}) { | ||||
| 1597 | $whole =~ s{ (\d) ( \d{3}(?:,|\z) ) }{$1,$2}xms | ||||
| 1598 | or last; | ||||
| 1599 | } | ||||
| 1600 | return $frac ? "$whole.$frac" : $whole; | ||||
| 1601 | } | ||||
| 1602 | |||||
| 1603 | die "Bad chunking option: $group\n" unless $group =~ /\A[0-3]\Z/; | ||||
| 1604 | my $sign = ($num =~ /\A\s*\+/) ? "plus" | ||||
| 1605 | : ($num =~ /\A\s*\-/) ? "minus" | ||||
| 1606 | : ''; | ||||
| 1607 | |||||
| 1608 | my ($zero, $one) = @arg{'zero','one'}; | ||||
| 1609 | my $comma = $arg{comma}; | ||||
| 1610 | my $and = $arg{'and'}; | ||||
| 1611 | |||||
| 1612 | my $ord = $num =~ s/(st|nd|rd|th)\Z//; | ||||
| 1613 | my @chunks = ($arg{decimal}) | ||||
| 1614 | ? $group ? split(/\./, $num) : split(/\./, $num, 2) | ||||
| 1615 | : ($num); | ||||
| 1616 | |||||
| 1617 | my $first = 1; | ||||
| 1618 | |||||
| 1619 | if ($chunks[0] eq '') { $first=0; shift @chunks; } | ||||
| 1620 | |||||
| 1621 | foreach ( @chunks ) | ||||
| 1622 | { | ||||
| 1623 | s/\D//g; | ||||
| 1624 | $_ = '0' unless $_; | ||||
| 1625 | |||||
| 1626 | if (!$group && !$first) { $_ = enword($_,1,$zero,$one,$comma,$and) } | ||||
| 1627 | else { $_ = enword($_,$group,$zero,$one,$comma,$and) } | ||||
| 1628 | |||||
| 1629 | s/, \Z//; | ||||
| 1630 | s/\s+,/,/g; | ||||
| 1631 | s/, (\S+)\s+\Z/ $and $1/ if !$group and $first; | ||||
| 1632 | s/\s+/ /g; | ||||
| 1633 | s/(\A\s|\s\Z)//g; | ||||
| 1634 | $first = '' if $first; | ||||
| 1635 | } | ||||
| 1636 | |||||
| 1637 | my @numchunks = (); | ||||
| 1638 | if ($first =~ /0/) | ||||
| 1639 | { | ||||
| 1640 | unshift @chunks, ''; | ||||
| 1641 | } | ||||
| 1642 | else | ||||
| 1643 | { | ||||
| 1644 | @numchunks = split /\Q$comma /, $chunks[0]; | ||||
| 1645 | } | ||||
| 1646 | |||||
| 1647 | $numchunks[-1] =~ s/($ordinal_suff)\Z/$ordinal{$1}/ | ||||
| 1648 | if $ord and @numchunks; | ||||
| 1649 | |||||
| 1650 | foreach (@chunks[1..$#chunks]) | ||||
| 1651 | { | ||||
| 1652 | push @numchunks, $arg{decimal}; | ||||
| 1653 | push @numchunks, split /\Q$comma /; | ||||
| 1654 | } | ||||
| 1655 | |||||
| 1656 | if (wantarray) | ||||
| 1657 | { | ||||
| 1658 | unshift @numchunks, $sign if $sign; | ||||
| 1659 | return @numchunks | ||||
| 1660 | } | ||||
| 1661 | elsif ($group) | ||||
| 1662 | { | ||||
| 1663 | return ($sign?"$sign ":'') . join ", ", @numchunks; | ||||
| 1664 | } | ||||
| 1665 | else | ||||
| 1666 | { | ||||
| 1667 | $num = ($sign?"$sign ":'') . shift @numchunks; | ||||
| 1668 | $first = ($num !~ /$arg{decimal}\Z/); | ||||
| 1669 | foreach ( @numchunks ) | ||||
| 1670 | { | ||||
| 1671 | if (/\A$arg{decimal}\Z/) | ||||
| 1672 | { | ||||
| 1673 | $num .= " $_"; | ||||
| 1674 | $first = 0; | ||||
| 1675 | } | ||||
| 1676 | elsif ($first) | ||||
| 1677 | { | ||||
| 1678 | $num .= "$comma $_"; | ||||
| 1679 | } | ||||
| 1680 | else | ||||
| 1681 | { | ||||
| 1682 | $num .= " $_"; | ||||
| 1683 | } | ||||
| 1684 | } | ||||
| 1685 | return $num; | ||||
| 1686 | } | ||||
| 1687 | } | ||||
| 1688 | |||||
| 1689 | # Join words with commas and a trailing 'and' (when appropriate)... | ||||
| 1690 | |||||
| 1691 | sub WORDLIST { | ||||
| 1692 | my %opt; | ||||
| 1693 | my @words; | ||||
| 1694 | |||||
| 1695 | for my $arg (@_) { | ||||
| 1696 | if (ref $arg eq 'HASH' ) { | ||||
| 1697 | %opt = (%opt, %{$arg}); | ||||
| 1698 | } | ||||
| 1699 | else { | ||||
| 1700 | push @words, $arg; | ||||
| 1701 | } | ||||
| 1702 | } | ||||
| 1703 | |||||
| 1704 | return "" if @words == 0; | ||||
| 1705 | return "$words[0]" if @words == 1; | ||||
| 1706 | |||||
| 1707 | my $conj = exists($opt{conj}) ? $opt{conj} : 'and'; | ||||
| 1708 | if (@words == 2) { | ||||
| 1709 | $conj =~ s/^ (?=\S) | (?<=\S) $/ /gxms; | ||||
| 1710 | return "$words[0]$conj$words[1]"; | ||||
| 1711 | } | ||||
| 1712 | |||||
| 1713 | my $sep = exists $opt{sep} ? $opt{sep} | ||||
| 1714 | : grep(/,/, @words) ? q{; } | ||||
| 1715 | : q{, } | ||||
| 1716 | ; | ||||
| 1717 | |||||
| 1718 | my $final_sep = !exists $opt{final_sep} ? "$sep $conj" | ||||
| 1719 | : length($opt{final_sep}) == 0 ? $conj | ||||
| 1720 | : "$opt{final_sep} $conj" | ||||
| 1721 | ; | ||||
| 1722 | $final_sep =~ s/\s+/ /gmxs; | ||||
| 1723 | $final_sep =~ s/^ (?=[^\W\d_]) | (?<=\S) $/ /gxms; | ||||
| 1724 | |||||
| 1725 | return join($sep, @words[0..@words-2]) . "$final_sep$words[-1]"; | ||||
| 1726 | } | ||||
| 1727 | |||||
| - - | |||||
| 1730 | 1 | 166µs | 1; | ||
| 1731 | |||||
| 1732 | __END__ | ||||
# spent 6µs within Lingua::EN::Inflect::CORE:fteread which was called:
# once (6µs+0s) by Pod::Wordlist::BEGIN@4 at line 855 | |||||
# spent 341ms (341+271µs) within Lingua::EN::Inflect::CORE:match which was called 75807 times, avg 5µs/call:
# 3612 times (1.62ms+0s) by Lingua::EN::Inflect::postprocess at line 863, avg 447ns/call
# 1220 times (3.56ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1210, avg 3µs/call
# 1220 times (3.17ms+0s) by Lingua::EN::Inflect::PL at line 873, avg 3µs/call
# 1220 times (1.37ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1197, avg 1µs/call
# 1220 times (1.25ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1192, avg 1µs/call
# 1220 times (1.20ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1205, avg 982ns/call
# 1220 times (1.13ms+0s) by Lingua::EN::Inflect::_PL_special_adjective at line 1266, avg 924ns/call
# 1220 times (1.04ms+0s) by Lingua::EN::Inflect::_PL_special_adjective at line 1276, avg 850ns/call
# 1220 times (1.01ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1182, avg 827ns/call
# 1220 times (942µs+0s) by Lingua::EN::Inflect::_PL_special_adjective at line 1281, avg 772ns/call
# 1220 times (928µs+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1202, avg 761ns/call
# 1220 times (848µs+0s) by Lingua::EN::Inflect::_PL_special_adjective at line 1284, avg 695ns/call
# 1182 times (8.09ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1040, avg 7µs/call
# 1176 times (50.1ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1087, avg 43µs/call
# 1176 times (26.8ms+271µs) by Lingua::EN::Inflect::_PL_noun at line 1051, avg 23µs/call
# 1176 times (4.06ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1102, avg 3µs/call
# 1176 times (4.01ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1075, avg 3µs/call
# 1176 times (3.64ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1049, avg 3µs/call
# 1176 times (3.44ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1096, avg 3µs/call
# 1176 times (3.24ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1057, avg 3µs/call
# 1176 times (3.13ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1095, avg 3µs/call
# 1176 times (2.43ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1093, avg 2µs/call
# 1176 times (2.35ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1068, avg 2µs/call
# 1176 times (2.08ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1092, avg 2µs/call
# 1176 times (2.05ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1089, avg 2µs/call
# 1176 times (1.81ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1100, avg 2µs/call
# 1176 times (1.74ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1062, avg 1µs/call
# 1176 times (1.62ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1101, avg 1µs/call
# 1176 times (1.57ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1094, avg 1µs/call
# 1176 times (1.33ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1091, avg 1µs/call
# 1176 times (1.21ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1081, avg 1µs/call
# 1175 times (25.3ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1108, avg 22µs/call
# 1175 times (22.2ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1109, avg 19µs/call
# 1175 times (13.2ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1110, avg 11µs/call
# 1175 times (9.97ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1111, avg 8µs/call
# 1175 times (7.11ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1105, avg 6µs/call
# 1175 times (6.85ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1106, avg 6µs/call
# 1175 times (6.20ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1112, avg 5µs/call
# 1175 times (5.29ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1107, avg 5µs/call
# 1175 times (4.27ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1140, avg 4µs/call
# 1175 times (3.23ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1216, avg 3µs/call
# 1175 times (2.89ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1104, avg 2µs/call
# 1175 times (1.44ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1103, avg 1µs/call
# 1175 times (410µs+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1211, avg 349ns/call
# 1175 times (352µs+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1212, avg 299ns/call
# 1174 times (964µs+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1218, avg 821ns/call
# 1173 times (3.72ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1220, avg 3µs/call
# 1173 times (1.28ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1223, avg 1µs/call
# 1173 times (738µs+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1221, avg 629ns/call
# 1158 times (476µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1141, avg 411ns/call
# 1131 times (1.30ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1143, avg 1µs/call
# 1131 times (783µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1142, avg 692ns/call
# 1129 times (3.02ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1144, avg 3µs/call
# 1086 times (3.63ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1152, avg 3µs/call
# 1086 times (3.61ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1150, avg 3µs/call
# 1086 times (3.33ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1156, avg 3µs/call
# 1086 times (3.16ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1149, avg 3µs/call
# 1086 times (2.57ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1151, avg 2µs/call
# 1083 times (407µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1157, avg 376ns/call
# 1080 times (3.99ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1158, avg 4µs/call
# 1050 times (55.5ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1162, avg 53µs/call
# 1047 times (691µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1163, avg 660ns/call
# 1043 times (538µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1164, avg 516ns/call | |||||
# spent 2µs within Lingua::EN::Inflect::CORE:qr which was called:
# once (2µs+0s) by Pod::Wordlist::BEGIN@4 at line 66 | |||||
# spent 34.1ms within Lingua::EN::Inflect::CORE:regcomp which was called 34192 times, avg 996ns/call:
# 1220 times (1.56ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1192, avg 1µs/call
# 1220 times (1.50ms+0s) by Lingua::EN::Inflect::_PL_special_adjective at line 1276, avg 1µs/call
# 1220 times (1.36ms+0s) by Lingua::EN::Inflect::_PL_special_adjective at line 1281, avg 1µs/call
# 1220 times (1.36ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1210, avg 1µs/call
# 1220 times (1.24ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1202, avg 1µs/call
# 1220 times (1.09ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1197, avg 889ns/call
# 1182 times (1.47ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1040, avg 1µs/call
# 1176 times (1.50ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1049, avg 1µs/call
# 1176 times (1.43ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1075, avg 1µs/call
# 1176 times (1.15ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1062, avg 981ns/call
# 1176 times (1.11ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1057, avg 946ns/call
# 1176 times (1.10ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1081, avg 934ns/call
# 1176 times (1.09ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1051, avg 926ns/call
# 1176 times (1.08ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1068, avg 922ns/call
# 1176 times (1.04ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1087, avg 881ns/call
# 1175 times (1.25ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1103, avg 1µs/call
# 1175 times (1.23ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1109, avg 1µs/call
# 1175 times (1.21ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1140, avg 1µs/call
# 1175 times (993µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1108, avg 845ns/call
# 1175 times (993µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1112, avg 845ns/call
# 1175 times (985µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1105, avg 838ns/call
# 1175 times (978µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1110, avg 833ns/call
# 1175 times (957µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1106, avg 814ns/call
# 1175 times (944µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1107, avg 803ns/call
# 1175 times (925µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1111, avg 787ns/call
# 1175 times (694µs+0s) by Lingua::EN::Inflect::_PL_noun at line 1104, avg 590ns/call
# 1173 times (1.46ms+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1220, avg 1µs/call
# 1131 times (1.03ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1142, avg 908ns/call
# 1050 times (1.30ms+0s) by Lingua::EN::Inflect::_PL_noun at line 1162, avg 1µs/call
# once (18µs+0s) by Pod::Wordlist::BEGIN@4 at line 66
# once (18µs+0s) by Lingua::EN::Inflect::_PL_special_adjective at line 1266
# once (7µs+0s) by Lingua::EN::Inflect::_PL_special_verb at line 1182 | |||||
# spent 10µs within Lingua::EN::Inflect::CORE:sort which was called:
# once (10µs+0s) by Pod::Wordlist::BEGIN@4 at line 214 | |||||
# spent 590µs within Lingua::EN::Inflect::CORE:subst which was called 1233 times, avg 478ns/call:
# 1220 times (577µs+0s) by Lingua::EN::Inflect::postprocess at line 862, avg 473ns/call
# 12 times (12µs+0s) by Pod::Wordlist::BEGIN@4 at line 1520, avg 975ns/call
# once (600ns+0s) by Pod::Wordlist::BEGIN@4 at line 850 |