1use std::collections::{ HashMap, HashSet };
2use regex::Regex;
3
4pub fn enclose(s: &str) -> String {
6 format!("(?:{})", s)
7}
8
9pub fn joinstem(cutpoint: Option<i32>, words: Option<Vec<String>>) -> String {
11 let words = words.unwrap_or_else(|| Vec::new());
12 let stem = words
13 .iter()
14 .map(|w| {
15 if let Some(c) = cutpoint {
16 if c < 0 { &w[..w.len() - (-c as usize)] } else { &w[..c as usize] }
17 } else {
18 w
19 }
20 })
21 .collect::<Vec<&str>>()
22 .join("|");
23 enclose(&stem)
24}
25
26pub fn bysize(words: Vec<String>) -> HashMap<usize, HashSet<String>> {
28 let mut res: HashMap<usize, HashSet<String>> = HashMap::new();
29 for word in words {
30 let len = word.len();
31 let entry = res.entry(len).or_insert_with(HashSet::new);
32 entry.insert(word.to_string());
33 }
34 res
35}
36
37pub fn make_pl_si_lists(
38 list: Vec<String>,
39 pl_ending: &str,
40 si_ending_size: Option<i32>,
41 do_joinstem: bool
42) -> (Vec<String>, HashMap<usize, HashSet<String>>, HashMap<usize, HashSet<String>>, String) {
43 let si_ending_size = si_ending_size.map(|size| -size);
44 let si_list: Vec<String> = list
45 .iter()
46 .map(|w| {
47 if let Some(size) = si_ending_size {
48 format!("{}{}", &w[..w.len() - (size as usize)], pl_ending)
49 } else {
50 format!("{}{}", w, pl_ending)
51 }
52 })
53 .collect();
54 let pl_bysize = bysize(list.clone());
55 let si_bysize = bysize(si_list.clone());
56 if do_joinstem {
57 let stem = joinstem(si_ending_size, Some(list));
58 (si_list, si_bysize, pl_bysize, stem)
59 } else {
60 (si_list, si_bysize, pl_bysize, String::new())
61 }
62}
63
64fn pl_sb_irregular_s() -> HashMap<String, String> {
65 return vec![
66 ("corpus", "corpuses|corpora"),
67 ("opus", "opuses|opera"),
68 ("genus", "genera"),
69 ("mythos", "mythoi"),
70 ("penis", "penises|penes"),
71 ("testis", "testes"),
72 ("atlas", "atlases|atlantes"),
73 ("yes", "yeses")
74 ]
75 .iter()
76 .map(|(k, v)| (k.to_string(), v.to_string()))
77 .collect();
78}
79
80fn pl_sb_irregular() -> HashMap<String, String> {
81 let mut pl_sb_irregular: HashMap<String, String> = vec![
82 ("child", "children"),
83 ("chili", "chilis|chilies"),
84 ("brother", "brothers|brethren"),
85 ("infinity", "infinities|infinity"),
86 ("loaf", "loaves"),
87 ("lore", "lores|lore"),
88 ("hoof", "hoofs|hooves"),
89 ("beef", "beefs|beeves"),
90 ("thief", "thiefs|thieves"),
91 ("money", "monies"),
92 ("mongoose", "mongooses"),
93 ("ox", "oxen"),
94 ("cow", "cows|kine"),
95 ("graffito", "graffiti"),
96 ("octopus", "octopuses|octopodes"),
97 ("genie", "genies|genii"),
98 ("ganglion", "ganglions|ganglia"),
99 ("trilby", "trilbys"),
100 ("turf", "turfs|turves"),
101 ("numen", "numina"),
102 ("atman", "atmas"),
103 ("occiput", "occiputs|occipita"),
104 ("sabretooth", "sabretooths"),
105 ("sabertooth", "sabertooths"),
106 ("lowlife", "lowlifes"),
107 ("flatfoot", "flatfoots"),
108 ("tenderfoot", "tenderfoots"),
109 ("romany", "romanies"),
110 ("jerry", "jerries"),
111 ("mary", "maries"),
112 ("talouse", "talouses"),
113 ("rom", "roma"),
114 ("carmen", "carmina")
115 ]
116 .iter()
117 .map(|(k, v)| (k.to_string(), v.to_string()))
118 .collect();
119 pl_sb_irregular.extend(pl_sb_irregular_s());
120 pl_sb_irregular
121}
122
123fn pl_sb_irregular_caps() -> HashMap<&'static str, &'static str> {
124 return vec![("Romany", "Romanies"), ("Jerry", "Jerrys"), ("Mary", "Marys"), ("Rom", "Roma")]
125 .into_iter()
126 .collect();
127}
128
129fn pl_sb_irregular_compound() -> HashMap<&'static str, &'static str> {
130 return vec![("prima donna", "prima donnas|prime donne")].into_iter().collect();
131}
132
133fn si_sb_irregular() -> HashMap<String, String> {
134 let mut si_sb_irregular: HashMap<String, String> = pl_sb_irregular()
135 .into_iter()
136 .map(|(k, v)| (v, k))
137 .collect();
138 let mut keys_to_remove = Vec::new();
139 let keys: Vec<String> = si_sb_irregular.keys().cloned().collect();
140 for k in keys.iter() {
141 if k.contains('|') {
142 keys_to_remove.push(k);
143 }
144 }
145 for k in keys_to_remove {
146 si_sb_irregular.remove(k);
147 let (k1, k2) = k.split_once('|').unwrap();
148 si_sb_irregular.insert(k1.to_string(), k.clone());
149 si_sb_irregular.insert(k2.to_string(), k.clone());
150 }
151 si_sb_irregular
152}
153
154fn si_sb_irregular_caps() -> HashMap<&'static str, &'static str> {
155 return pl_sb_irregular_caps()
156 .iter()
157 .map(|(&k, &v)| (v, k))
158 .collect();
159}
160
161fn si_sb_irregular_compound() -> HashMap<&'static str, &'static str> {
162 let mut si_sb_irregular_compound: HashMap<&str, &str> = pl_sb_irregular_compound()
163 .iter()
164 .map(|(&k, &v)| (v, k))
165 .collect();
166 let mut keys_to_remove = Vec::new();
167 for &k in si_sb_irregular_compound.keys() {
168 if k.contains('|') {
169 keys_to_remove.push(k);
170 }
171 }
172 for k in keys_to_remove {
173 si_sb_irregular_compound.remove(&k);
174 let (k1, k2) = k.split_once('|').unwrap();
175 si_sb_irregular_compound.insert(k1, k);
176 si_sb_irregular_compound.insert(k2, k);
177 }
178 si_sb_irregular_compound
179}
180
181fn pl_sb_z_zes_list() -> Vec<String> {
182 return vec!["quartz", "topaz"]
183 .iter()
184 .map(|s| s.to_string())
185 .collect();
186}
187
188fn pl_sb_z_zes_bysize() -> HashMap<usize, HashSet<String>> {
189 return bysize(pl_sb_z_zes_list());
190}
191
192fn sb_ze_zes_list() -> Vec<String> {
193 return vec!["snooze"]
194 .iter()
195 .map(|s| s.to_string())
196 .collect();
197}
198
199fn sb_ze_zes_bysize() -> HashMap<usize, HashSet<String>> {
200 return bysize(sb_ze_zes_list());
201}
202
203fn pl_sb_c_is_ides_complete() -> Vec<String> {
204 return vec!["ephemeris", "iris", "clitoris", "chrysalis", "epididymis"]
205 .iter()
206 .map(|s| s.to_string())
207 .collect();
208}
209
210fn pl_sb_c_is_ides_endings() -> Vec<String> {
211 return vec!["itis"]
212 .iter()
213 .map(|s| s.to_string())
214 .collect();
215}
216
217fn pl_sb_c_is_ides() -> String {
218 let pl_sb_c_is_ides: Vec<String> = pl_sb_c_is_ides_complete()
219 .iter()
220 .map(|s| s.to_string())
221 .chain(
222 pl_sb_c_is_ides_endings()
223 .into_iter()
224 .map(|w| format!(".*{}", w))
225 )
226 .collect();
227 return joinstem(Some(-2), Some(pl_sb_c_is_ides));
228}
229
230fn pl_sb_c_is_ides_list() -> Vec<String> {
231 let mut pl_sb_c_is_ides_complete = pl_sb_c_is_ides_complete();
232 pl_sb_c_is_ides_complete.append(&mut pl_sb_c_is_ides_endings());
233 pl_sb_c_is_ides_complete
234}
235
236fn si_sb_c_is_ides_list() -> Vec<String> {
237 return make_pl_si_lists(pl_sb_c_is_ides_list(), "ides", Some(2), false).0;
238}
239
240fn si_sb_c_is_ides_bysize() -> HashMap<usize, HashSet<String>> {
241 return make_pl_si_lists(pl_sb_c_is_ides_list(), "ides", Some(2), false).1;
242}
243
244fn pl_sb_c_is_ides_bysize() -> HashMap<usize, HashSet<String>> {
245 return make_pl_si_lists(pl_sb_c_is_ides_list(), "ides", Some(2), false).2;
246}
247
248fn pl_sb_c_a_ata_list() -> Vec<String> {
249 return vec![
250 "anathema",
251 "bema",
252 "carcinoma",
253 "charisma",
254 "diploma",
255 "dogma",
256 "drama",
257 "edema",
258 "enema",
259 "enigma",
260 "lemma",
261 "lymphoma",
262 "magma",
263 "melisma",
264 "miasma",
265 "oedema",
266 "sarcoma",
267 "schema",
268 "soma",
269 "stigma",
270 "stoma",
271 "trauma",
272 "gumma",
273 "pragma"
274 ]
275 .iter()
276 .map(|s| s.to_string())
277 .collect();
278}
279
280fn si_sb_c_a_ata_list() -> Vec<String> {
281 return make_pl_si_lists(pl_sb_c_a_ata_list(), "ata", Some(1), true).0;
282}
283
284fn si_sb_c_a_ata_bysize() -> HashMap<usize, HashSet<String>> {
285 return make_pl_si_lists(pl_sb_c_a_ata_list(), "ata", Some(1), true).1;
286}
287
288fn pl_sb_c_a_ata_bysize() -> HashMap<usize, HashSet<String>> {
289 return make_pl_si_lists(pl_sb_c_a_ata_list(), "ata", Some(1), true).2;
290}
291
292fn pl_sb_c_a_ata() -> String {
293 return make_pl_si_lists(pl_sb_c_a_ata_list(), "ata", Some(1), true).3;
294}
295
296fn pl_sb_u_a_ae_list() -> Vec<String> {
297 return vec!["alumna", "alga", "vertebra", "persona", "vita"]
298 .iter()
299 .map(|s| s.to_string())
300 .collect();
301}
302
303fn si_sb_u_a_ae_list() -> Vec<String> {
304 return make_pl_si_lists(pl_sb_u_a_ae_list(), "e", None, true).0;
305}
306
307fn si_sb_u_a_ae_bysize() -> HashMap<usize, HashSet<String>> {
308 return make_pl_si_lists(pl_sb_u_a_ae_list(), "e", None, true).1;
309}
310
311fn pl_sb_u_a_ae_bysize() -> HashMap<usize, HashSet<String>> {
312 return make_pl_si_lists(pl_sb_u_a_ae_list(), "e", None, true).2;
313}
314
315fn pl_sb_u_a_ae() -> String {
316 return make_pl_si_lists(pl_sb_u_a_ae_list(), "e", None, true).3;
317}
318
319fn pl_sb_c_a_ae_list() -> Vec<String> {
320 return vec![
321 "amoeba",
322 "antenna",
323 "formula",
324 "hyperbola",
325 "medusa",
326 "nebula",
327 "parabola",
328 "abscissa",
329 "hydra",
330 "nova",
331 "lacuna",
332 "aurora",
333 "umbra",
334 "flora",
335 "fauna"
336 ]
337 .iter()
338 .map(|s| s.to_string())
339 .collect();
340}
341
342fn si_sb_c_a_ae_list() -> Vec<String> {
343 return make_pl_si_lists(pl_sb_c_a_ae_list(), "e", None, true).0;
344}
345
346fn si_sb_c_a_ae_bysize() -> HashMap<usize, HashSet<String>> {
347 return make_pl_si_lists(pl_sb_c_a_ae_list(), "e", None, true).1;
348}
349
350fn pl_sb_c_a_ae_bysize() -> HashMap<usize, HashSet<String>> {
351 return make_pl_si_lists(pl_sb_c_a_ae_list(), "e", None, true).2;
352}
353
354fn pl_sb_c_a_ae() -> String {
355 return make_pl_si_lists(pl_sb_c_a_ae_list(), "e", None, true).3;
356}
357
358fn pl_sb_c_en_ina_list() -> Vec<String> {
359 return vec!["stamen", "foramen", "lumen"]
360 .iter()
361 .map(|s| s.to_string())
362 .collect();
363}
364
365fn si_sb_c_en_ina_list() -> Vec<String> {
366 return make_pl_si_lists(pl_sb_c_en_ina_list(), "ina", Some(2), true).0;
367}
368
369fn si_sb_c_en_ina_bysize() -> HashMap<usize, HashSet<String>> {
370 return make_pl_si_lists(pl_sb_c_en_ina_list(), "ina", Some(2), true).1;
371}
372
373fn pl_sb_c_en_ina_bysize() -> HashMap<usize, HashSet<String>> {
374 return make_pl_si_lists(pl_sb_c_en_ina_list(), "ina", Some(2), true).2;
375}
376
377fn pl_sb_c_en_ina() -> String {
378 return make_pl_si_lists(pl_sb_c_en_ina_list(), "ina", Some(2), true).3;
379}
380
381fn pl_sb_u_um_a_list() -> Vec<String> {
382 return vec![
383 "bacterium",
384 "agendum",
385 "desideratum",
386 "erratum",
387 "stratum",
388 "datum",
389 "ovum",
390 "extremum",
391 "candelabrum"
392 ]
393 .iter()
394 .map(|s| s.to_string())
395 .collect();
396}
397
398fn si_sb_u_um_a_list() -> Vec<String> {
399 return make_pl_si_lists(pl_sb_u_um_a_list(), "a", Some(2), true).0;
400}
401
402fn si_sb_u_um_a_bysize() -> HashMap<usize, HashSet<String>> {
403 return make_pl_si_lists(pl_sb_u_um_a_list(), "a", Some(2), true).1;
404}
405
406fn pl_sb_u_um_a_bysize() -> HashMap<usize, HashSet<String>> {
407 return make_pl_si_lists(pl_sb_u_um_a_list(), "a", Some(2), true).2;
408}
409
410fn pl_sb_u_um_a() -> String {
411 return make_pl_si_lists(pl_sb_u_um_a_list(), "a", Some(2), true).3;
412}
413
414fn pl_sb_c_um_a_list() -> Vec<String> {
415 return vec![
416 "maximum",
417 "minimum",
418 "momentum",
419 "optimum",
420 "quantum",
421 "cranium",
422 "curriculum",
423 "dictum",
424 "phylum",
425 "aquarium",
426 "compendium",
427 "emporium",
428 "encomium",
429 "gymnasium",
430 "honorarium",
431 "interregnum",
432 "lustrum",
433 "memorandum",
434 "millennium",
435 "rostrum",
436 "spectrum",
437 "speculum",
438 "stadium",
439 "trapezium",
440 "ultimatum",
441 "medium",
442 "vacuum",
443 "velum",
444 "consortium",
445 "arboretum"
446 ]
447 .iter()
448 .map(|s| s.to_string())
449 .collect();
450}
451
452fn si_sb_c_um_a_list() -> Vec<String> {
453 return make_pl_si_lists(pl_sb_c_um_a_list(), "a", Some(2), true).0;
454}
455
456fn si_sb_c_um_a_bysize() -> HashMap<usize, HashSet<String>> {
457 return make_pl_si_lists(pl_sb_c_um_a_list(), "a", Some(2), true).1;
458}
459
460fn pl_sb_c_um_a_bysize() -> HashMap<usize, HashSet<String>> {
461 return make_pl_si_lists(pl_sb_c_um_a_list(), "a", Some(2), true).2;
462}
463
464fn pl_sb_c_um_a() -> String {
465 return make_pl_si_lists(pl_sb_c_um_a_list(), "a", Some(2), true).3;
466}
467
468fn pl_sb_u_us_i_list() -> Vec<String> {
469 return vec![
470 "alumnus",
471 "alveolus",
472 "bacillus",
473 "bronchus",
474 "locus",
475 "nucleus",
476 "stimulus",
477 "meniscus",
478 "sarcophagus"
479 ]
480 .iter()
481 .map(|s| s.to_string())
482 .collect();
483}
484
485fn si_sb_u_us_i_list() -> Vec<String> {
486 return make_pl_si_lists(pl_sb_u_us_i_list(), "i", Some(2), true).0;
487}
488
489fn si_sb_u_us_i_bysize() -> HashMap<usize, HashSet<String>> {
490 return make_pl_si_lists(pl_sb_u_us_i_list(), "i", Some(2), true).1;
491}
492
493fn pl_sb_u_us_i_bysize() -> HashMap<usize, HashSet<String>> {
494 return make_pl_si_lists(pl_sb_u_us_i_list(), "i", Some(2), true).2;
495}
496
497fn pl_sb_u_us_i() -> String {
498 return make_pl_si_lists(pl_sb_u_us_i_list(), "i", Some(2), true).3;
499}
500
501fn pl_sb_c_us_i_list() -> Vec<String> {
502 return vec![
503 "focus",
504 "radius",
505 "genius",
506 "incubus",
507 "succubus",
508 "nimbus",
509 "fungus",
510 "nucleolus",
511 "stylus",
512 "torus",
513 "umbilicus",
514 "uterus",
515 "hippopotamus",
516 "cactus"
517 ]
518 .iter()
519 .map(|s| s.to_string())
520 .collect();
521}
522
523fn si_sb_c_us_i_list() -> Vec<String> {
524 return make_pl_si_lists(pl_sb_c_us_i_list(), "i", Some(2), true).0;
525}
526
527fn si_sb_c_us_i_bysize() -> HashMap<usize, HashSet<String>> {
528 return make_pl_si_lists(pl_sb_c_us_i_list(), "i", Some(2), true).1;
529}
530
531fn pl_sb_c_us_i_bysize() -> HashMap<usize, HashSet<String>> {
532 return make_pl_si_lists(pl_sb_c_us_i_list(), "i", Some(2), true).2;
533}
534
535fn pl_sb_c_us_i() -> String {
536 return make_pl_si_lists(pl_sb_c_us_i_list(), "i", Some(2), true).3;
537}
538
539fn pl_sb_c_us_us() -> Vec<String> {
540 return vec!["status", "apparatus", "prospectus", "sinus", "hiatus", "impetus", "plexus"]
541 .iter()
542 .map(|s| s.to_string())
543 .collect();
544}
545
546fn pl_sb_c_us_us_bysize() -> HashMap<usize, HashSet<String>> {
547 return bysize(pl_sb_c_us_us());
548}
549
550fn pl_sb_u_on_a_list() -> Vec<String> {
551 return vec![
552 "criterion",
553 "perihelion",
554 "aphelion",
555 "phenomenon",
556 "prolegomenon",
557 "noumenon",
558 "organon",
559 "asyndeton",
560 "hyperbaton"
561 ]
562 .iter()
563 .map(|s| s.to_string())
564 .collect();
565}
566
567fn si_sb_u_on_a_list() -> Vec<String> {
568 return make_pl_si_lists(pl_sb_u_on_a_list(), "a", Some(2), true).0;
569}
570
571fn si_sb_u_on_a_bysize() -> HashMap<usize, HashSet<String>> {
572 return make_pl_si_lists(pl_sb_u_on_a_list(), "a", Some(2), true).1;
573}
574
575fn pl_sb_u_on_a_bysize() -> HashMap<usize, HashSet<String>> {
576 return make_pl_si_lists(pl_sb_u_on_a_list(), "a", Some(2), true).2;
577}
578
579fn pl_sb_u_on_a() -> String {
580 return make_pl_si_lists(pl_sb_u_on_a_list(), "a", Some(2), true).3;
581}
582
583fn pl_sb_c_on_a_list() -> Vec<String> {
584 return vec!["oxymoron"]
585 .iter()
586 .map(|s| s.to_string())
587 .collect();
588}
589
590fn si_sb_c_on_a_list() -> Vec<String> {
591 return make_pl_si_lists(pl_sb_c_on_a_list(), "a", Some(2), true).0;
592}
593
594fn si_sb_c_on_a_bysize() -> HashMap<usize, HashSet<String>> {
595 return make_pl_si_lists(pl_sb_c_on_a_list(), "a", Some(2), true).1;
596}
597
598fn pl_sb_c_on_a_bysize() -> HashMap<usize, HashSet<String>> {
599 return make_pl_si_lists(pl_sb_c_on_a_list(), "a", Some(2), true).2;
600}
601
602fn pl_sb_c_on_a() -> String {
603 return make_pl_si_lists(pl_sb_c_on_a_list(), "a", Some(2), true).3;
604}
605
606fn pl_sb_c_o_i() -> Vec<String> {
607 return vec!["solo", "soprano", "basso", "alto", "contralto", "tempo", "piano", "virtuoso"]
608 .iter()
609 .map(|s| s.to_string())
610 .collect();
611}
612
613fn pl_sb_c_o_i_bysize() -> HashMap<usize, HashSet<String>> {
614 return bysize(pl_sb_c_o_i());
615}
616
617fn si_sb_c_o_i_bysize() -> HashMap<usize, HashSet<String>> {
618 return bysize(
619 pl_sb_c_o_i()
620 .iter()
621 .map(|w| format!("{}i", &w[..w.len() - 1]))
622 .collect()
623 );
624}
625
626fn pl_sb_c_o_i_stems() -> String {
627 return joinstem(Some(-1), Some(pl_sb_c_o_i()));
628}
629
630fn pl_sb_u_o_os_complete() -> Vec<String> {
631 return vec!["ado", "ISO", "NATO", "NCO", "NGO", "oto"]
632 .iter()
633 .map(|s| s.to_string())
634 .collect();
635}
636
637fn si_sb_u_o_os_complete() -> Vec<String> {
638 return pl_sb_u_o_os_complete()
639 .iter()
640 .map(|w| format!("{}s", w))
641 .collect();
642}
643
644fn pl_sb_u_o_os_endings() -> Vec<String> {
645 let mut pl_sb_u_o_os_endings: Vec<String> = vec![
646 "aficionado",
647 "aggro",
648 "albino",
649 "allegro",
650 "ammo",
651 "Antananarivo",
652 "archipelago",
653 "armadillo",
654 "auto",
655 "avocado",
656 "Bamako",
657 "Barquisimeto",
658 "bimbo",
659 "bingo",
660 "Biro",
661 "bolero",
662 "Bolzano",
663 "bongo",
664 "Boto",
665 "burro",
666 "Cairo",
667 "canto",
668 "cappuccino",
669 "casino",
670 "cello",
671 "Chicago",
672 "Chimango",
673 "cilantro",
674 "cochito",
675 "coco",
676 "Colombo",
677 "Colorado",
678 "commando",
679 "concertino",
680 "contango",
681 "credo",
682 "crescendo",
683 "cyano",
684 "demo",
685 "ditto",
686 "Draco",
687 "dynamo",
688 "embryo",
689 "Esperanto",
690 "espresso",
691 "euro",
692 "falsetto",
693 "Faro",
694 "fiasco",
695 "Filipino",
696 "flamenco",
697 "furioso",
698 "generalissimo",
699 "Gestapo",
700 "ghetto",
701 "gigolo",
702 "gizmo",
703 "Greensboro",
704 "gringo",
705 "Guaiabero",
706 "guano",
707 "gumbo",
708 "gyro",
709 "hairdo",
710 "hippo",
711 "Idaho",
712 "impetigo",
713 "inferno",
714 "info",
715 "intermezzo",
716 "intertrigo",
717 "Iquico",
718 "jumbo",
719 "junto",
720 "Kakapo",
721 "kilo",
722 "Kinkimavo",
723 "Kokako",
724 "Kosovo",
725 "Lesotho",
726 "libero",
727 "libido",
728 "libretto",
729 "lido",
730 "Lilo",
731 "limbo",
732 "limo",
733 "lineno",
734 "lingo",
735 "lino",
736 "livedo",
737 "loco",
738 "logo",
739 "lumbago",
740 "macho",
741 "macro",
742 "mafioso",
743 "magneto",
744 "magnifico",
745 "Majuro",
746 "Malabo",
747 "manifesto",
748 "Maputo",
749 "Maracaibo",
750 "medico",
751 "memo",
752 "metro",
753 "Mexico",
754 "micro",
755 "Milano",
756 "Monaco",
757 "mono",
758 "Montenegro",
759 "Morocco",
760 "Muqdisho",
761 "myo",
762 "neutrino",
763 "Ningbo",
764 "octavo",
765 "oregano",
766 "Orinoco",
767 "Orlando",
768 "Oslo",
769 "panto",
770 "Paramaribo",
771 "Pardusco",
772 "pedalo",
773 "photo",
774 "pimento",
775 "pinto",
776 "pleco",
777 "Pluto",
778 "pogo",
779 "polo",
780 "poncho",
781 "Porto-Novo",
782 "Porto",
783 "pro",
784 "psycho",
785 "pueblo",
786 "quarto",
787 "Quito",
788 "repo",
789 "rhino",
790 "risotto",
791 "rococo",
792 "rondo",
793 "Sacramento",
794 "saddo",
795 "sago",
796 "salvo",
797 "Santiago",
798 "Sapporo",
799 "Sarajevo",
800 "scherzando",
801 "scherzo",
802 "silo",
803 "sirocco",
804 "sombrero",
805 "staccato",
806 "sterno",
807 "stucco",
808 "stylo",
809 "sumo",
810 "Taiko",
811 "techno",
812 "terrazzo",
813 "testudo",
814 "timpano",
815 "tiro",
816 "tobacco",
817 "Togo",
818 "Tokyo",
819 "torero",
820 "Torino",
821 "Toronto",
822 "torso",
823 "tremolo",
824 "typo",
825 "tyro",
826 "ufo",
827 "UNESCO",
828 "vaquero",
829 "vermicello",
830 "verso",
831 "vibrato",
832 "violoncello",
833 "Virgo",
834 "weirdo",
835 "WHO",
836 "WTO",
837 "Yamoussoukro",
838 "yo-yo",
839 "zero",
840 "Zibo"
841 ]
842 .iter()
843 .map(|s| s.to_string())
844 .collect();
845 pl_sb_u_o_os_endings.extend(pl_sb_c_o_i());
846 pl_sb_u_o_os_endings
847}
848
849fn pl_sb_u_o_os_bysize() -> HashMap<usize, HashSet<String>> {
850 return bysize(pl_sb_u_o_os_endings());
851}
852
853fn si_sb_u_o_os_bysize() -> HashMap<usize, HashSet<String>> {
854 return bysize(
855 pl_sb_u_o_os_endings()
856 .iter()
857 .map(|w| format!("{}s", w))
858 .collect()
859 );
860}
861
862fn pl_sb_u_ch_chs_list() -> Vec<String> {
863 return vec!["czech", "eunuch", "stomach"]
864 .iter()
865 .map(|s| s.to_string())
866 .collect();
867}
868
869fn si_sb_u_ch_chs_list() -> Vec<String> {
870 return make_pl_si_lists(pl_sb_u_ch_chs_list(), "s", None, true).0;
871}
872
873fn si_sb_u_ch_chs_bysize() -> HashMap<usize, HashSet<String>> {
874 return make_pl_si_lists(pl_sb_u_ch_chs_list(), "s", None, true).1;
875}
876
877fn pl_sb_u_ch_chs_bysize() -> HashMap<usize, HashSet<String>> {
878 return make_pl_si_lists(pl_sb_u_ch_chs_list(), "s", None, true).2;
879}
880
881fn pl_sb_u_ch_chs() -> String {
882 return make_pl_si_lists(pl_sb_u_ch_chs_list(), "s", None, true).3;
883}
884
885fn pl_sb_u_ex_ices_list() -> Vec<String> {
886 return vec!["codex", "murex", "silex"]
887 .iter()
888 .map(|s| s.to_string())
889 .collect();
890}
891
892fn si_sb_u_ex_ices_list() -> Vec<String> {
893 return make_pl_si_lists(pl_sb_u_ex_ices_list(), "ices", Some(2), true).0;
894}
895
896fn si_sb_u_ex_ices_bysize() -> HashMap<usize, HashSet<String>> {
897 return make_pl_si_lists(pl_sb_u_ex_ices_list(), "ices", Some(2), true).1;
898}
899
900fn pl_sb_u_ex_ices_bysize() -> HashMap<usize, HashSet<String>> {
901 return make_pl_si_lists(pl_sb_u_ex_ices_list(), "ices", Some(2), true).2;
902}
903
904fn pl_sb_u_ex_ices() -> String {
905 return make_pl_si_lists(pl_sb_u_ex_ices_list(), "ices", Some(2), true).3;
906}
907
908fn pl_sb_u_ix_ices_list() -> Vec<String> {
909 return vec!["radix", "helix"]
910 .iter()
911 .map(|s| s.to_string())
912 .collect();
913}
914
915fn si_sb_u_ix_ices_list() -> Vec<String> {
916 return make_pl_si_lists(pl_sb_u_ix_ices_list(), "ices", Some(2), true).0;
917}
918
919fn si_sb_u_ix_ices_bysize() -> HashMap<usize, HashSet<String>> {
920 return make_pl_si_lists(pl_sb_u_ix_ices_list(), "ices", Some(2), true).1;
921}
922
923fn pl_sb_u_ix_ices_bysize() -> HashMap<usize, HashSet<String>> {
924 return make_pl_si_lists(pl_sb_u_ix_ices_list(), "ices", Some(2), true).2;
925}
926
927fn pl_sb_u_ix_ices() -> String {
928 return make_pl_si_lists(pl_sb_u_ix_ices_list(), "ices", Some(2), true).3;
929}
930
931fn pl_sb_c_ex_ices_list() -> Vec<String> {
932 return vec!["vortex", "vertex", "cortex", "latex", "pontifex", "apex", "index", "simplex"]
933 .iter()
934 .map(|s| s.to_string())
935 .collect();
936}
937
938fn si_sb_c_ex_ices_list() -> Vec<String> {
939 return make_pl_si_lists(pl_sb_c_ex_ices_list(), "ices", Some(2), true).0;
940}
941
942fn si_sb_c_ex_ices_bysize() -> HashMap<usize, HashSet<String>> {
943 return make_pl_si_lists(pl_sb_c_ex_ices_list(), "ices", Some(2), true).1;
944}
945
946fn pl_sb_c_ex_ices_bysize() -> HashMap<usize, HashSet<String>> {
947 return make_pl_si_lists(pl_sb_c_ex_ices_list(), "ices", Some(2), true).2;
948}
949
950fn pl_sb_c_ex_ices() -> String {
951 return make_pl_si_lists(pl_sb_c_ex_ices_list(), "ices", Some(2), true).3;
952}
953
954fn pl_sb_c_ix_ices_list() -> Vec<String> {
955 return vec!["appendix"]
956 .iter()
957 .map(|s| s.to_string())
958 .collect();
959}
960
961fn si_sb_c_ix_ices_list() -> Vec<String> {
962 return make_pl_si_lists(pl_sb_c_ix_ices_list(), "ices", Some(2), true).0;
963}
964
965fn si_sb_c_ix_ices_bysize() -> HashMap<usize, HashSet<String>> {
966 return make_pl_si_lists(pl_sb_c_ix_ices_list(), "ices", Some(2), true).1;
967}
968
969fn pl_sb_c_ix_ices_bysize() -> HashMap<usize, HashSet<String>> {
970 return make_pl_si_lists(pl_sb_c_ix_ices_list(), "ices", Some(2), true).2;
971}
972
973fn pl_sb_c_ix_ices() -> String {
974 return make_pl_si_lists(pl_sb_c_ix_ices_list(), "ices", Some(2), true).3;
975}
976
977fn pl_sb_c_i_list() -> Vec<String> {
978 return vec!["afreet", "afrit", "efreet"]
979 .iter()
980 .map(|s| s.to_string())
981 .collect();
982}
983
984fn si_sb_c_i_list() -> Vec<String> {
985 return make_pl_si_lists(pl_sb_c_i_list(), "i", None, true).0;
986}
987
988fn si_sb_c_i_bysize() -> HashMap<usize, HashSet<String>> {
989 return make_pl_si_lists(pl_sb_c_i_list(), "i", None, true).1;
990}
991
992fn pl_sb_c_i_bysize() -> HashMap<usize, HashSet<String>> {
993 return make_pl_si_lists(pl_sb_c_i_list(), "i", None, true).2;
994}
995
996fn pl_sb_c_i() -> String {
997 return make_pl_si_lists(pl_sb_c_i_list(), "i", None, true).3;
998}
999
1000fn pl_sb_c_im_list() -> Vec<String> {
1001 return vec!["goy", "seraph", "cherub"]
1002 .iter()
1003 .map(|s| s.to_string())
1004 .collect();
1005}
1006
1007fn si_sb_c_im_list() -> Vec<String> {
1008 return make_pl_si_lists(pl_sb_c_im_list(), "im", None, true).0;
1009}
1010
1011fn si_sb_c_im_bysize() -> HashMap<usize, HashSet<String>> {
1012 return make_pl_si_lists(pl_sb_c_im_list(), "im", None, true).1;
1013}
1014
1015fn pl_sb_c_im_bysize() -> HashMap<usize, HashSet<String>> {
1016 return make_pl_si_lists(pl_sb_c_im_list(), "im", None, true).2;
1017}
1018
1019fn pl_sb_c_im() -> String {
1020 return make_pl_si_lists(pl_sb_c_im_list(), "im", None, true).3;
1021}
1022
1023fn pl_sb_u_man_mans_list() -> Vec<String> {
1024 return vec![
1025 "ataman",
1026 "caiman",
1027 "cayman",
1028 "ceriman",
1029 "desman",
1030 "dolman",
1031 "farman",
1032 "harman",
1033 "hetman",
1034 "human",
1035 "leman",
1036 "ottoman",
1037 "shaman",
1038 "talisman"
1039 ]
1040 .iter()
1041 .map(|s| s.to_string())
1042 .collect();
1043}
1044
1045fn pl_sb_u_man_mans_caps_list() -> Vec<String> {
1046 return vec![
1047 "Alabaman",
1048 "Bahaman",
1049 "Burman",
1050 "|German",
1051 "Hiroshiman",
1052 "Liman",
1053 "Nakayaman",
1054 "Norman",
1055 "Oklahoman",
1056 "Panaman",
1057 "Roman",
1058 "Selman",
1059 "Sonaman",
1060 "Tacoman",
1061 "Yakiman",
1062 "Yokohaman",
1063 "Yuman"
1064 ]
1065 .iter()
1066 .map(|s| s.to_string())
1067 .collect();
1068}
1069
1070fn si_sb_u_man_mans_list() -> Vec<String> {
1071 return make_pl_si_lists(pl_sb_u_man_mans_list(), "s", None, false).0;
1072}
1073
1074fn si_sb_u_man_mans_caps_list() -> Vec<String> {
1075 return make_pl_si_lists(pl_sb_u_man_mans_caps_list(), "s", None, false).0;
1076}
1077
1078fn si_sb_u_man_mans_bysize() -> HashMap<usize, HashSet<String>> {
1079 return make_pl_si_lists(pl_sb_u_man_mans_list(), "s", None, false).1;
1080}
1081
1082fn si_sb_u_man_mans_caps_bysize() -> HashMap<usize, HashSet<String>> {
1083 return make_pl_si_lists(pl_sb_u_man_mans_caps_list(), "s", None, false).1;
1084}
1085
1086fn pl_sb_u_man_mans_bysize() -> HashMap<usize, HashSet<String>> {
1087 return make_pl_si_lists(pl_sb_u_man_mans_list(), "s", None, false).2;
1088}
1089
1090fn pl_sb_u_man_mans_caps_bysize() -> HashMap<usize, HashSet<String>> {
1091 return make_pl_si_lists(pl_sb_u_man_mans_caps_list(), "s", None, false).2;
1092}
1093
1094fn pl_sb_u_louse_lice_list() -> Vec<String> {
1095 return vec!["booklouse", "grapelouse", "louse", "woodlouse"]
1096 .iter()
1097 .map(|s| s.to_string())
1098 .collect();
1099}
1100
1101fn si_sb_u_louse_lice_list() -> Vec<String> {
1102 return make_pl_si_lists(pl_sb_u_louse_lice_list(), "lice", Some(5), false).0;
1103}
1104
1105fn si_sb_u_louse_lice_bysize() -> HashMap<usize, HashSet<String>> {
1106 return make_pl_si_lists(pl_sb_u_louse_lice_list(), "lice", Some(5), false).1;
1107}
1108
1109fn pl_sb_u_louse_lice_bysize() -> HashMap<usize, HashSet<String>> {
1110 return make_pl_si_lists(pl_sb_u_louse_lice_list(), "lice", Some(5), false).2;
1111}
1112
1113fn pl_sb_uninflected_s_complete() -> Vec<String> {
1114 return vec![
1115 "breeches",
1116 "britches",
1117 "pajamas",
1118 "pyjamas",
1119 "clippers",
1120 "gallows",
1121 "hijinks",
1122 "headquarters",
1123 "pliers",
1124 "scissors",
1125 "testes",
1126 "herpes",
1127 "pincers",
1128 "shears",
1129 "proceedings",
1130 "trousers",
1131 "cantus",
1132 "coitus",
1133 "nexus",
1134 "contretemps",
1135 "corps",
1136 "debris",
1137 "siemens",
1138 "mumps",
1139 "diabetes",
1140 "jackanapes",
1141 "series",
1142 "species",
1143 "subspecies",
1144 "rabies",
1145 "chassis",
1146 "innings",
1147 "news",
1148 "mews",
1149 "haggis"
1150 ]
1151 .iter()
1152 .map(|s| s.to_string())
1153 .collect();
1154}
1155
1156fn pl_sb_uninflected_s_endings() -> Vec<String> {
1157 return vec!["ois", "measles"]
1158 .iter()
1159 .map(|s| s.to_string())
1160 .collect();
1161}
1162
1163fn pl_sb_uninflected_s() -> Vec<String> {
1164 let mut pl_sb_uninflected_s = pl_sb_uninflected_s_complete();
1165 pl_sb_uninflected_s.extend(
1166 pl_sb_uninflected_s_endings()
1167 .iter()
1168 .map(|w| format!(".*{}", w))
1169 );
1170 pl_sb_uninflected_s
1171}
1172
1173fn pl_sb_uninflected_herd() -> Vec<String> {
1174 return vec![
1175 "wildebeest",
1176 "swine",
1177 "eland",
1178 "bison",
1179 "buffalo",
1180 "cattle",
1181 "elk",
1182 "rhinoceros",
1183 "zucchini",
1184 "caribou",
1185 "dace",
1186 "grouse",
1187 "guinea fowl",
1188 "guinea-fowl",
1189 "haddock",
1190 "hake",
1191 "halibut",
1192 "herring",
1193 "mackerel",
1194 "pickerel",
1195 "pike",
1196 "roe",
1197 "seed",
1198 "shad",
1199 "snipe",
1200 "teal",
1201 "turbot",
1202 "water fowl",
1203 "water-fowl"
1204 ]
1205 .iter()
1206 .map(|s| s.to_string())
1207 .collect();
1208}
1209
1210fn pl_sb_uninflected_complete() -> Vec<String> {
1211 return vec![
1212 "tuna",
1213 "salmon",
1214 "mackerel",
1215 "trout",
1216 "bream",
1217 "sea-bass",
1218 "sea bass",
1219 "carp",
1220 "cod",
1221 "flounder",
1222 "whiting",
1223 "moose",
1224 "graffiti",
1225 "djinn",
1226 "samuri",
1227 "offspring",
1228 "pence",
1229 "quid",
1230 "hertz"
1231 ]
1232 .iter()
1233 .map(|s| s.to_string())
1234 .chain(pl_sb_uninflected_complete())
1235 .collect();
1236}
1237
1238fn pl_sb_uninflected_caps() -> Vec<String> {
1239 return vec![
1240 "Portuguese",
1241 "Amoyese",
1242 "Borghese",
1243 "Congoese",
1244 "Faroese",
1245 "Foochowese",
1246 "Genevese",
1247 "Genoese",
1248 "Gilbertese",
1249 "Hottentotese",
1250 "Kiplingese",
1251 "Kongoese",
1252 "Lucchese",
1253 "Maltese",
1254 "Nankingese",
1255 "Niasese",
1256 "Pekingese",
1257 "Piedmontese",
1258 "Pistoiese",
1259 "Sarawakese",
1260 "Shavese",
1261 "Vermontese",
1262 "Wenchowese",
1263 "Yengeese"
1264 ]
1265 .iter()
1266 .map(|s| s.to_string())
1267 .collect();
1268}
1269
1270fn pl_sb_uninflected_endings() -> Vec<String> {
1271 return vec![
1272 "butter",
1273 "cash",
1274 "furniture",
1275 "information",
1276 "fish",
1277 "deer",
1278 "sheep",
1279 "nese",
1280 "rese",
1281 "lese",
1282 "mese",
1283 "pox",
1284 "craft"
1285 ]
1286 .iter()
1287 .map(|s| s.to_string())
1288 .chain(pl_sb_uninflected_s_endings())
1289 .collect();
1290}
1291
1292fn pl_sb_uninflected_bysize() -> HashMap<usize, HashSet<String>> {
1293 return bysize(pl_sb_uninflected_endings());
1294}
1295
1296fn pl_sb_singular_s_complete() -> Vec<String> {
1297 return vec![
1298 "acropolis",
1299 "aegis",
1300 "alias",
1301 "asbestos",
1302 "bathos",
1303 "bias",
1304 "bronchitis",
1305 "bursitis",
1306 "caddis",
1307 "cannabis",
1308 "canvas",
1309 "chaos",
1310 "cosmos",
1311 "dais",
1312 "digitalis",
1313 "epidermis",
1314 "ethos",
1315 "eyas",
1316 "gas",
1317 "glottis",
1318 "hubris",
1319 "ibis",
1320 "lens",
1321 "mantis",
1322 "marquis",
1323 "metropolis",
1324 "pathos",
1325 "pelvis",
1326 "polis",
1327 "rhinoceros",
1328 "sassafras",
1329 "trellis"
1330 ]
1331 .iter()
1332 .map(|s| s.to_string())
1333 .chain(pl_sb_c_is_ides_complete())
1334 .collect();
1335}
1336
1337fn pl_sb_singular_s_endings() -> Vec<String> {
1338 return vec!["ss", "us"]
1339 .iter()
1340 .map(|s| s.to_string())
1341 .chain(pl_sb_c_is_ides_endings())
1342 .collect();
1343}
1344
1345fn pl_sb_singular_s_bysize() -> HashMap<usize, HashSet<String>> {
1346 return bysize(pl_sb_singular_s_endings());
1347}
1348
1349fn si_sb_singular_s_complete() -> Vec<String> {
1350 return pl_sb_singular_s_complete()
1351 .iter()
1352 .map(|w| format!("{}es", w))
1353 .collect();
1354}
1355
1356fn si_sb_singular_s_endings() -> Vec<String> {
1357 return pl_sb_singular_s_endings()
1358 .iter()
1359 .map(|w| format!("{}es", w))
1360 .collect();
1361}
1362
1363fn si_sb_singular_s_bysize() -> HashMap<usize, HashSet<String>> {
1364 return bysize(si_sb_singular_s_endings());
1365}
1366
1367fn pl_sb_singular_s_es() -> Vec<String> {
1368 return vec!["[A-Z].*es"]
1369 .iter()
1370 .map(|s| s.to_string())
1371 .collect();
1372}
1373
1374fn pl_sb_singular_s() -> String {
1375 let mut concat: Vec<String> = Vec::new();
1376 concat.extend(
1377 pl_sb_singular_s_complete()
1378 .iter()
1379 .map(|w| w.to_string())
1380 );
1381 concat.extend(
1382 pl_sb_singular_s_endings()
1383 .iter()
1384 .map(|w| format!(".*{}", w))
1385 );
1386 concat.extend(
1387 pl_sb_singular_s_es()
1388 .iter()
1389 .map(|w| w.to_string())
1390 );
1391 return enclose(&concat.join("|"));
1392}
1393
1394fn si_sb_ois_oi_case() -> Vec<String> {
1395 return vec!["Bolshois", "Hanois"]
1396 .iter()
1397 .map(|s| s.to_string())
1398 .collect();
1399}
1400
1401fn si_sb_uses_use_case() -> Vec<String> {
1402 return vec!["Betelgeuses", "Duses", "Meuses", "Syracuses", "Toulouses"]
1403 .iter()
1404 .map(|s| s.to_string())
1405 .collect();
1406}
1407
1408fn si_sb_use_uses() -> Vec<String> {
1409 return vec![
1410 "abuses",
1411 "applauses",
1412 "blouses",
1413 "carouses",
1414 "causes",
1415 "chartreuses",
1416 "clauses",
1417 "contuses",
1418 "douses",
1419 "excuses",
1420 "fuses",
1421 "grouses",
1422 "hypotenuses",
1423 "masseuses",
1424 "menopauses",
1425 "misuses",
1426 "muses",
1427 "overuses",
1428 "pauses",
1429 "peruses",
1430 "profuses",
1431 "recluses",
1432 "reuses",
1433 "ruses",
1434 "souses",
1435 "spouses",
1436 "suffuses",
1437 "transfuses",
1438 "uses"
1439 ]
1440 .iter()
1441 .map(|s| s.to_string())
1442 .collect();
1443}
1444
1445fn si_sb_ies_ie_case() -> Vec<String> {
1446 return vec![
1447 "Addies",
1448 "Aggies",
1449 "Allies",
1450 "Amies",
1451 "Angies",
1452 "Annies",
1453 "Annmaries",
1454 "Archies",
1455 "Arties",
1456 "Aussies",
1457 "Barbies",
1458 "Barries",
1459 "Basies",
1460 "Bennies",
1461 "Bernies",
1462 "Berties",
1463 "Bessies",
1464 "Betties",
1465 "Billies",
1466 "Blondies",
1467 "Bobbies",
1468 "Bonnies",
1469 "Bowies",
1470 "Brandies",
1471 "Bries",
1472 "Brownies",
1473 "Callies",
1474 "Carnegies",
1475 "Carries",
1476 "Cassies",
1477 "Charlies",
1478 "Cheries",
1479 "Christies",
1480 "Connies",
1481 "Curies",
1482 "Dannies",
1483 "Debbies",
1484 "Dixies",
1485 "Dollies",
1486 "Donnies",
1487 "Drambuies",
1488 "Eddies",
1489 "Effies",
1490 "Ellies",
1491 "Elsies",
1492 "Eries",
1493 "Ernies",
1494 "Essies",
1495 "Eugenies",
1496 "Fannies",
1497 "Flossies",
1498 "Frankies",
1499 "Freddies",
1500 "Gillespies",
1501 "Goldies",
1502 "Gracies",
1503 "Guthries",
1504 "Hallies",
1505 "Hatties",
1506 "Hetties",
1507 "Hollies",
1508 "Jackies",
1509 "Jamies",
1510 "Janies",
1511 "Jannies",
1512 "Jeanies",
1513 "Jeannies",
1514 "Jennies",
1515 "Jessies",
1516 "Jimmies",
1517 "Jodies",
1518 "Johnies",
1519 "Johnnies",
1520 "Josies",
1521 "Julies",
1522 "Kalgoorlies",
1523 "Kathies",
1524 "Katies",
1525 "Kellies",
1526 "Kewpies",
1527 "Kristies",
1528 "Laramies",
1529 "Lassies",
1530 "Lauries",
1531 "Leslies",
1532 "Lessies",
1533 "Lillies",
1534 "Lizzies",
1535 "Lonnies",
1536 "Lories",
1537 "Lorries",
1538 "Lotties",
1539 "Louies",
1540 "Mackenzies",
1541 "Maggies",
1542 "Maisies",
1543 "Mamies",
1544 "Marcies",
1545 "Margies",
1546 "Maries",
1547 "Marjories",
1548 "Matties",
1549 "McKenzies",
1550 "Melanies",
1551 "Mickies",
1552 "Millies",
1553 "Minnies",
1554 "Mollies",
1555 "Mounties",
1556 "Nannies",
1557 "Natalies",
1558 "Nellies",
1559 "Netties",
1560 "Ollies",
1561 "Ozzies",
1562 "Pearlies",
1563 "Pottawatomies",
1564 "Reggies",
1565 "Richies",
1566 "Rickies",
1567 "Robbies",
1568 "Ronnies",
1569 "Rosalies",
1570 "Rosemaries",
1571 "Rosies",
1572 "Roxies",
1573 "Rushdies",
1574 "Ruthies",
1575 "Sadies",
1576 "Sallies",
1577 "Sammies",
1578 "Scotties",
1579 "Selassies",
1580 "Sherries",
1581 "Sophies",
1582 "Stacies",
1583 "Stefanies",
1584 "Stephanies",
1585 "Stevies",
1586 "Susies",
1587 "Sylvies",
1588 "Tammies",
1589 "Terries",
1590 "Tessies",
1591 "Tommies",
1592 "Tracies",
1593 "Trekkies",
1594 "Valaries",
1595 "Valeries",
1596 "Valkyries",
1597 "Vickies",
1598 "Virgies",
1599 "Willies",
1600 "Winnies",
1601 "Wylies",
1602 "Yorkies"
1603 ]
1604 .iter()
1605 .map(|s| s.to_string())
1606 .collect();
1607}
1608
1609fn si_sb_ies_ie() -> Vec<String> {
1610 return vec![
1611 "aeries",
1612 "baggies",
1613 "belies",
1614 "biggies",
1615 "birdies",
1616 "bogies",
1617 "bonnies",
1618 "boogies",
1619 "bookies",
1620 "bourgeoisies",
1621 "brownies",
1622 "budgies",
1623 "caddies",
1624 "calories",
1625 "camaraderies",
1626 "cockamamies",
1627 "collies",
1628 "cookies",
1629 "coolies",
1630 "cooties",
1631 "coteries",
1632 "crappies",
1633 "curies",
1634 "cutesies",
1635 "dogies",
1636 "eyries",
1637 "floozies",
1638 "footsies",
1639 "freebies",
1640 "genies",
1641 "goalies",
1642 "groupies",
1643 "hies",
1644 "jalousies",
1645 "junkies",
1646 "kiddies",
1647 "laddies",
1648 "lassies",
1649 "lies",
1650 "lingeries",
1651 "magpies",
1652 "menageries",
1653 "mommies",
1654 "movies",
1655 "neckties",
1656 "newbies",
1657 "nighties",
1658 "oldies",
1659 "organdies",
1660 "overlies",
1661 "pies",
1662 "pinkies",
1663 "pixies",
1664 "potpies",
1665 "prairies",
1666 "quickies",
1667 "reveries",
1668 "rookies",
1669 "rotisseries",
1670 "softies",
1671 "sorties",
1672 "species",
1673 "stymies",
1674 "sweeties",
1675 "ties",
1676 "underlies",
1677 "unties",
1678 "veggies",
1679 "vies",
1680 "yuppies",
1681 "zombies"
1682 ]
1683 .iter()
1684 .map(|s| s.to_string())
1685 .collect();
1686}
1687
1688fn si_sb_oes_oe_case() -> Vec<String> {
1689 return vec![
1690 "Chloes",
1691 "Crusoes",
1692 "Defoes",
1693 "Faeroes",
1694 "Ivanhoes",
1695 "Joes",
1696 "McEnroes",
1697 "Moes",
1698 "Monroes",
1699 "Noes",
1700 "Poes",
1701 "Roscoes",
1702 "Tahoes",
1703 "Tippecanoes",
1704 "Zoes"
1705 ]
1706 .iter()
1707 .map(|s| s.to_string())
1708 .collect();
1709}
1710
1711fn si_sb_oes_oe() -> Vec<String> {
1712 return vec![
1713 "aloes",
1714 "backhoes",
1715 "canoes",
1716 "does",
1717 "floes",
1718 "foes",
1719 "hoes",
1720 "mistletoes",
1721 "oboes",
1722 "pekoes",
1723 "roes",
1724 "sloes",
1725 "throes",
1726 "tiptoes",
1727 "toes",
1728 "woes"
1729 ]
1730 .iter()
1731 .map(|s| s.to_string())
1732 .collect();
1733}
1734
1735fn si_sb_z_zes() -> Vec<String> {
1736 return vec!["quartzes", "topazes"]
1737 .iter()
1738 .map(|s| s.to_string())
1739 .collect();
1740}
1741
1742fn si_sb_zzes_zz() -> Vec<String> {
1743 return vec!["buzzes", "fizzes", "frizzes", "razzes"]
1744 .iter()
1745 .map(|s| s.to_string())
1746 .collect();
1747}
1748
1749fn si_sb_ches_che_case() -> Vec<String> {
1750 return vec![
1751 "Andromaches",
1752 "Apaches",
1753 "Blanches",
1754 "Comanches",
1755 "Nietzsches",
1756 "Porsches",
1757 "Roches"
1758 ]
1759 .iter()
1760 .map(|s| s.to_string())
1761 .collect();
1762}
1763
1764fn si_sb_ches_che() -> Vec<String> {
1765 return vec![
1766 "aches",
1767 "avalanches",
1768 "backaches",
1769 "bellyaches",
1770 "caches",
1771 "cloches",
1772 "creches",
1773 "douches",
1774 "earaches",
1775 "fiches",
1776 "headaches",
1777 "heartaches",
1778 "microfiches",
1779 "niches",
1780 "pastiches",
1781 "psyches",
1782 "quiches",
1783 "stomachaches",
1784 "toothaches",
1785 "tranches"
1786 ]
1787 .iter()
1788 .map(|s| s.to_string())
1789 .collect();
1790}
1791
1792fn si_sb_xes_xe() -> Vec<String> {
1793 return vec!["annexes", "axes", "deluxes", "pickaxes"]
1794 .iter()
1795 .map(|s| s.to_string())
1796 .collect();
1797}
1798
1799fn si_sb_sses_sse_case() -> Vec<String> {
1800 return vec!["Hesses", "Jesses", "Larousses", "Matisses"]
1801 .iter()
1802 .map(|s| s.to_string())
1803 .collect();
1804}
1805
1806fn si_sb_sses_sse() -> Vec<String> {
1807 return vec!["bouillabaisses", "crevasses", "demitasses", "impasses", "mousses", "posses"]
1808 .iter()
1809 .map(|s| s.to_string())
1810 .collect();
1811}
1812
1813fn si_sb_ves_ve_case() -> Vec<String> {
1814 return vec!["Clives", "Palmolives"]
1815 .iter()
1816 .map(|s| s.to_string())
1817 .collect();
1818}
1819
1820fn si_sb_ves_ve() -> Vec<String> {
1821 return vec![
1822 "interweaves",
1823 "weaves",
1824 "olives",
1825 "bivalves",
1826 "dissolves",
1827 "resolves",
1828 "salves",
1829 "twelves",
1830 "valves"
1831 ]
1832 .iter()
1833 .map(|s| s.to_string())
1834 .collect();
1835}
1836
1837fn plverb_special_s() -> String {
1838 let mut concat: Vec<String> = Vec::new();
1839 concat.push(pl_sb_singular_s());
1840 concat.extend(pl_sb_uninflected_s());
1841 let pl_sb_irregular_s_keys: Vec<String> = pl_sb_irregular_s().keys().cloned().collect();
1842 concat.extend(pl_sb_irregular_s_keys);
1843 concat.extend(
1844 vec!["(.*[csx])is", "(.*)ceps", "[A-Z].*s"]
1845 .iter()
1846 .map(|s| s.to_string())
1847 );
1848 return enclose(&concat.join("|"));
1849}
1850
1851fn _pl_sb_postfix_adj_defn() -> HashMap<String, String> {
1852 let mut m = HashMap::new();
1853 m.insert("general".to_string(), enclose(r"(?!major|lieutenant|brigadier|adjutant|.*star)\S+"));
1854 m.insert("martial".to_string(), enclose("court"));
1855 m.insert("force".to_string(), enclose("pound"));
1856 m
1857}
1858
1859fn pl_sb_postfix_adj() -> Vec<String> {
1860 return _pl_sb_postfix_adj_defn()
1861 .iter()
1862 .map(|(k, v)| format!("{}(?=(?:-|\\s+){})", v, k))
1863 .collect();
1864}
1865
1866fn pl_sb_postfix_adj_stems() -> String {
1867 return format!("({})(.*)", pl_sb_postfix_adj().join("|"));
1868}
1869
1870fn si_sb_es_is() -> Vec<String> {
1871 return vec![
1872 "amanuenses",
1873 "amniocenteses",
1874 "analyses",
1875 "antitheses",
1876 "apotheoses",
1877 "arterioscleroses",
1878 "atheroscleroses",
1879 "axes",
1880 "catalyses",
1881 "catharses",
1882 "chasses",
1883 "cirrhoses",
1884 "cocces",
1885 "crises",
1886 "diagnoses",
1887 "dialyses",
1888 "diereses",
1889 "electrolyses",
1890 "emphases",
1891 "exegeses",
1892 "geneses",
1893 "halitoses",
1894 "hydrolyses",
1895 "hypnoses",
1896 "hypotheses",
1897 "hystereses",
1898 "metamorphoses",
1899 "metastases",
1900 "misdiagnoses",
1901 "mitoses",
1902 "mononucleoses",
1903 "narcoses",
1904 "necroses",
1905 "nemeses",
1906 "neuroses",
1907 "oases",
1908 "osmoses",
1909 "osteoporoses",
1910 "paralyses",
1911 "parentheses",
1912 "parthenogeneses",
1913 "periphrases",
1914 "photosyntheses",
1915 "probosces",
1916 "prognoses",
1917 "prophylaxes",
1918 "prostheses",
1919 "preces",
1920 "psoriases",
1921 "psychoanalyses",
1922 "psychokineses",
1923 "psychoses",
1924 "scleroses",
1925 "scolioses",
1926 "sepses",
1927 "silicoses",
1928 "symbioses",
1929 "synopses",
1930 "syntheses",
1931 "taxes",
1932 "telekineses",
1933 "theses",
1934 "thromboses",
1935 "tuberculoses",
1936 "urinalyses"
1937 ]
1938 .iter()
1939 .map(|s| s.to_string())
1940 .collect();
1941}
1942
1943fn pl_prep_list() -> Vec<String> {
1944 return vec![
1945 "about",
1946 "above",
1947 "across",
1948 "after",
1949 "among",
1950 "around",
1951 "at",
1952 "athwart",
1953 "before",
1954 "behind",
1955 "below",
1956 "beneath",
1957 "beside",
1958 "besides",
1959 "between",
1960 "betwixt",
1961 "beyond",
1962 "but",
1963 "by",
1964 "during",
1965 "except",
1966 "for",
1967 "from",
1968 "in",
1969 "into",
1970 "near",
1971 "of",
1972 "off",
1973 "on",
1974 "onto",
1975 "out",
1976 "over",
1977 "since",
1978 "till",
1979 "to",
1980 "under",
1981 "until",
1982 "unto",
1983 "upon",
1984 "with"
1985 ]
1986 .iter()
1987 .map(|s| s.to_string())
1988 .collect();
1989}
1990
1991fn pl_prep_list_da() -> Vec<String> {
1992 let mut concat = pl_prep_list();
1993 concat.push("de".to_string());
1994 concat.push("du".to_string());
1995 concat.push("da".to_string());
1996 return concat;
1997}
1998
1999fn pl_prep_bysize() -> HashMap<usize, HashSet<String>> {
2000 return bysize(pl_prep_list_da());
2001}
2002
2003fn pl_prep() -> String {
2004 return enclose(&pl_prep_list_da().join("|"));
2005}
2006
2007fn pl_sb_prep_dual_compound() -> String {
2008 return format!(r"(.*?)((?:-|\s+)(?:{})(?:-|\s+))a(?:-|\s+)(.*)", pl_prep());
2009}
2010
2011fn singular_pronoun_genders() -> Vec<String> {
2012 return vec![
2013 "neuter",
2014 "feminine",
2015 "masculine",
2016 "gender-neutral",
2017 "feminine or masculine",
2018 "masculine or feminine"
2019 ]
2020 .iter()
2021 .map(|s| s.to_string())
2022 .collect();
2023}
2024
2025fn pl_pron_nom() -> HashMap<String, String> {
2026 return vec![
2027 ("i", "we"),
2028 ("myself", "ourselves"),
2029 ("you", "you"),
2030 ("yourself", "yourselves"),
2031 ("she", "they"),
2032 ("herself", "themselves"),
2033 ("he", "they"),
2034 ("himself", "themselves"),
2035 ("it", "they"),
2036 ("itself", "themselves"),
2037 ("they", "they"),
2038 ("themself", "themselves"),
2039 ("mine", "ours"),
2040 ("yours", "yours"),
2041 ("hers", "theirs"),
2042 ("his", "theirs"),
2043 ("its", "theirs"),
2044 ("theirs", "theirs")
2045 ]
2046 .iter()
2047 .map(|&(k, v)| (k.to_string(), v.to_string()))
2048 .collect();
2049}
2050
2051fn pl_pron_acc() -> HashMap<String, String> {
2052 return vec![
2053 ("me", "us"),
2054 ("myself", "ourselves"),
2055 ("you", "you"),
2056 ("yourself", "yourselves"),
2057 ("her", "them"),
2058 ("herself", "themselves"),
2059 ("it", "them"),
2060 ("itself", "themselves"),
2061 ("them", "them"),
2062 ("themself", "themselves")
2063 ]
2064 .iter()
2065 .map(|&(k, v)| (k.to_string(), v.to_string()))
2066 .collect();
2067}
2068
2069fn pl_pron_acc_keys() -> String {
2070 return enclose(&pl_pron_acc().keys().cloned().collect::<Vec<String>>().join("|"));
2071}
2072
2073fn pl_pron_acc_keys_bysize() -> HashMap<usize, HashSet<String>> {
2074 return bysize(pl_pron_acc().keys().cloned().collect::<Vec<String>>());
2075}
2076
2077fn pron_tuples() -> Vec<(&'static str, &'static str, &'static str, &'static str)> {
2078 return vec![
2079 ("nom", "they", "neuter", "it"),
2080 ("nom", "they", "feminine", "she"),
2081 ("nom", "they", "masculine", "he"),
2082 ("nom", "they", "gender-neutral", "they"),
2083 ("nom", "they", "feminine or masculine", "she or he"),
2084 ("nom", "they", "masculine or feminine", "he or she"),
2085 ("nom", "themselves", "neuter", "itself"),
2086 ("nom", "themselves", "feminine", "herself"),
2087 ("nom", "themselves", "masculine", "himself"),
2088 ("nom", "themselves", "gender-neutral", "themself"),
2089 ("nom", "themselves", "feminine or masculine", "herself or himself"),
2090 ("nom", "themselves", "masculine or feminine", "himself or herself"),
2091 ("nom", "theirs", "neuter", "its"),
2092 ("nom", "theirs", "feminine", "hers"),
2093 ("nom", "theirs", "masculine", "his"),
2094 ("nom", "theirs", "gender-neutral", "theirs"),
2095 ("nom", "theirs", "feminine or masculine", "hers or his"),
2096 ("nom", "theirs", "masculine or feminine", "his or hers"),
2097 ("acc", "them", "neuter", "it"),
2098 ("acc", "them", "feminine", "her"),
2099 ("acc", "them", "masculine", "him"),
2100 ("acc", "them", "gender-neutral", "them"),
2101 ("acc", "them", "feminine or masculine", "her or him"),
2102 ("acc", "them", "masculine or feminine", "him or her"),
2103 ("acc", "themselves", "neuter", "itself"),
2104 ("acc", "themselves", "feminine", "herself"),
2105 ("acc", "themselves", "masculine", "himself"),
2106 ("acc", "themselves", "gender-neutral", "themself"),
2107 ("acc", "themselves", "feminine or masculine", "herself or himself"),
2108 ("acc", "themselves", "masculine or feminine", "himself or herself")
2109 ];
2110}
2111
2112fn si_pron() -> HashMap<String, HashMap<String, HashMap<String, String>>> {
2113 let mut si_pron: HashMap<String, HashMap<String, HashMap<String, String>>> = HashMap::new();
2114 let mut nom: HashMap<String, HashMap<String, String>> = HashMap::new();
2115 for (k, v) in pl_pron_nom() {
2116 let mut entry = HashMap::new();
2117 entry.insert(k.to_string(), v.to_string());
2118 nom.insert(k.to_string(), entry);
2119 }
2120 let mut acc: HashMap<String, HashMap<String, String>> = HashMap::new();
2122 for (k, v) in pl_pron_acc() {
2123 let mut entry = HashMap::new();
2124 entry.insert(k.to_string(), v.to_string());
2125 acc.insert(k.to_string(), entry);
2126 }
2127 si_pron.insert("nom".to_string(), nom);
2128 si_pron.insert("acc".to_string(), acc);
2129
2130 for data in pron_tuples() {
2131 let (this_case, this_plur, this_gend, this_sing) = data;
2132 let case = si_pron.entry(this_case.to_string()).or_insert_with(HashMap::new);
2133 let plur = case.entry(this_plur.to_string()).or_insert_with(HashMap::new);
2134 plur.insert(this_gend.to_string(), this_sing.to_string());
2135 }
2136
2137 si_pron
2138}
2139
2140pub fn get_si_pron(thecase: &str, word: &str, gender: Option<&str>) -> String {
2141 match si_pron().get(thecase) {
2142 Some(case) =>
2143 match case.get(word) {
2144 Some(sing) =>
2145 match sing.get(gender.unwrap_or("N/A")) {
2146 Some(specific) => specific.clone(),
2147 None => sing.clone().values().next().unwrap().clone(),
2148 }
2149 None => panic!("No such case for word: {}", word),
2150 }
2151 None => panic!("No such case: {}", thecase),
2152 }
2153}
2154
2155fn plverb_irregular_pres() -> HashMap<String, String> {
2156 return vec![
2157 ("am", "are"),
2158 ("are", "are"),
2159 ("is", "are"),
2160 ("was", "were"),
2161 ("were", "were"),
2162 ("have", "have"),
2163 ("has", "have"),
2164 ("do", "do"),
2165 ("does", "do")
2166 ]
2167 .iter()
2168 .map(|&(k, v)| (k.to_string(), v.to_string()))
2169 .collect();
2170}
2171
2172fn plverb_ambiguous_pres() -> HashMap<String, String> {
2173 return vec![
2174 ("act", "act"),
2175 ("acts", "act"),
2176 ("blame", "blame"),
2177 ("blames", "blame"),
2178 ("can", "can"),
2179 ("must", "must"),
2180 ("fly", "fly"),
2181 ("flies", "fly"),
2182 ("copy", "copy"),
2183 ("copies", "copy"),
2184 ("drink", "drink"),
2185 ("drinks", "drink"),
2186 ("fight", "fight"),
2187 ("fights", "fight"),
2188 ("fire", "fire"),
2189 ("fires", "fire"),
2190 ("like", "like"),
2191 ("likes", "like"),
2192 ("look", "look"),
2193 ("looks", "look"),
2194 ("make", "make"),
2195 ("makes", "make"),
2196 ("reach", "reach"),
2197 ("reaches", "reach"),
2198 ("run", "run"),
2199 ("runs", "run"),
2200 ("sink", "sink"),
2201 ("sinks", "sink"),
2202 ("sleep", "sleep"),
2203 ("sleeps", "sleep"),
2204 ("view", "view"),
2205 ("views", "view")
2206 ]
2207 .iter()
2208 .map(|&(k, v)| (k.to_string(), v.to_string()))
2209 .collect();
2210}
2211
2212fn plverb_ambiguous_pres_keys() -> Regex {
2213 let pattern = format!(
2214 r"^({})((\s.*)?)$",
2215 enclose(&plverb_ambiguous_pres().keys().cloned().collect::<Vec<String>>().join("|"))
2216 );
2217 return Regex::new(&pattern).expect("Failed to compile regex");
2218}
2219
2220fn plverb_irregular_non_pres() -> Vec<String> {
2221 return vec![
2222 "did",
2223 "had",
2224 "ate",
2225 "made",
2226 "put",
2227 "spent",
2228 "fought",
2229 "sank",
2230 "gave",
2231 "sought",
2232 "shall",
2233 "could",
2234 "ought",
2235 "should"
2236 ]
2237 .iter()
2238 .map(|s| s.to_string())
2239 .collect();
2240}
2241
2242fn plverb_ambiguous_non_pres() -> Regex {
2243 let pattern = format!(r"^((?:thought|saw|bent|will|might|cut))((\s.*)?)$");
2244 return Regex::new(&pattern).expect("Failed to compile regex");
2245}
2246
2247fn pl_v_oes_oe() -> Vec<String> {
2248 return vec!["canoes", "floes", "oboes", "roes", "throes", "woes"]
2249 .iter()
2250 .map(|s| s.to_string())
2251 .collect();
2252}
2253
2254fn pl_v_oes_oe_endings_size4() -> Vec<String> {
2255 return vec!["hoes", "toes"]
2256 .iter()
2257 .map(|s| s.to_string())
2258 .collect();
2259}
2260
2261fn pl_v_oes_oe_endings_size5() -> Vec<String> {
2262 return vec!["shoes"]
2263 .iter()
2264 .map(|s| s.to_string())
2265 .collect();
2266}
2267
2268fn pl_count_zero() -> Vec<String> {
2269 return vec!["0", "no", "zero", "nil"]
2270 .iter()
2271 .map(|s| s.to_string())
2272 .collect();
2273}
2274
2275fn pl_count_one() -> Vec<String> {
2276 return vec!["1", "a", "an", "one", "each", "every", "this", "that"]
2277 .iter()
2278 .map(|s| s.to_string())
2279 .collect();
2280}
2281
2282fn pl_adj_special() -> HashMap<String, String> {
2283 return vec![("a", "some"), ("an", "some"), ("this", "these"), ("that", "those")]
2284 .iter()
2285 .map(|&(k, v)| (k.to_string(), v.to_string()))
2286 .collect();
2287}
2288
2289fn pl_adj_special_keys() -> Regex {
2290 let pattern = format!(
2291 r"^({})$",
2292 enclose(&pl_adj_special().keys().cloned().collect::<Vec<String>>().join("|"))
2293 );
2294 return Regex::new(&pattern).expect("Failed to compile regex");
2295}
2296
2297fn pl_adj_poss() -> HashMap<String, String> {
2298 return vec![
2299 ("my", "our"),
2300 ("your", "your"),
2301 ("its", "their"),
2302 ("her", "their"),
2303 ("his", "their"),
2304 ("their", "their")
2305 ]
2306 .iter()
2307 .map(|&(k, v)| (k.to_string(), v.to_string()))
2308 .collect();
2309}
2310
2311fn pl_adj_poss_keys() -> Regex {
2312 let pattern = format!(
2313 r"^({})$",
2314 enclose(&pl_adj_poss().keys().cloned().collect::<Vec<String>>().join("|"))
2315 );
2316 return Regex::new(&pattern).expect("Failed to compile regex");
2317}
2318
2319fn a_abbrev() -> Regex {
2320 return Regex::new(
2321 r"^(?:FJO|[HLMNS]Y\.|RY[EO]|SQU|(?:F[LR]?|[HL]|MN?|N|RH?|S[CHKLMNPTVW]?|X(?:YL)?) [AEIOU])[FHLMNRSX][A-Z]"
2322 ).expect("Failed to compile regex");
2323}
2324
2325fn a_y_cons() -> Regex {
2326 return Regex::new(r"^(y(b[lor]|cl[ea]|fere|gg|p[ios]|rou|tt))").expect(
2327 "Failed to compile regex"
2328 );
2329}
2330
2331fn a_explicit_a() -> Regex {
2332 return Regex::new(r"^((?:unabomber|unanimous|US))").expect("Failed to compile regex");
2333}
2334
2335fn a_explicit_an() -> Regex {
2336 return Regex::new(r"^((?:euler|hour(?!i)|heir|honest|hono[ur]|mpeg))").expect(
2337 "Failed to compile regex"
2338 );
2339}
2340
2341fn a_ordinal_a() -> Regex {
2342 return Regex::new(r"^([aefhilmnorsx]-?th)").expect("Failed to compile regex");
2343}
2344
2345fn a_ordinal_an() -> Regex {
2346 return Regex::new(r"^([bcdgjkpqtuvwyz]-?th)").expect("Failed to compile regex");
2347}
2348
2349fn nth() -> HashMap<u32, String> {
2350 return vec![
2351 (0, "th"),
2352 (1, "st"),
2353 (2, "nd"),
2354 (3, "rd"),
2355 (4, "th"),
2356 (5, "th"),
2357 (6, "th"),
2358 (7, "th"),
2359 (8, "th"),
2360 (9, "th"),
2361 (11, "th"),
2362 (12, "th"),
2363 (13, "th")
2364 ]
2365 .iter()
2366 .map(|&(k, v)| (k, v.to_string()))
2367 .collect();
2368}
2369
2370fn nth_suff() -> HashSet<String> {
2371 return nth().values().cloned().collect();
2372}
2373
2374fn ordinal() -> HashMap<String, String> {
2375 return vec![
2376 ("ty", "tieth"),
2377 ("one", "first"),
2378 ("two", "second"),
2379 ("three", "third"),
2380 ("five", "fifth"),
2381 ("eight", "eighth"),
2382 ("nine", "ninth"),
2383 ("twelve", "twelfth")
2384 ]
2385 .iter()
2386 .map(|&(k, v)| (k.to_string(), v.to_string()))
2387 .collect();
2388}
2389
2390pub fn ordinal_suff() -> Regex {
2391 let pattern = format!("({})", ordinal().keys().cloned().collect::<Vec<String>>().join("|"));
2392 return Regex::new(&format!("{}\\z", pattern)).expect("Failed to compile regex");
2393}
2394
2395fn unit() -> Vec<String> {
2396 return vec!["", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine"]
2397 .iter()
2398 .map(|s| s.to_string())
2399 .collect();
2400}
2401
2402fn teen() -> Vec<String> {
2403 return vec![
2404 "ten",
2405 "eleven",
2406 "twelve",
2407 "thirteen",
2408 "fourteen",
2409 "fifteen",
2410 "sixteen",
2411 "seventeen",
2412 "eighteen",
2413 "nineteen"
2414 ]
2415 .iter()
2416 .map(|s| s.to_string())
2417 .collect();
2418}
2419
2420fn ten() -> Vec<String> {
2421 return vec![
2422 "",
2423 "",
2424 "twenty",
2425 "thirty",
2426 "forty",
2427 "fifty",
2428 "sixty",
2429 "seventy",
2430 "eighty",
2431 "ninety"
2432 ]
2433 .iter()
2434 .map(|s| s.to_string())
2435 .collect();
2436}
2437
2438fn mill() -> Vec<String> {
2439 return vec![
2440 " ",
2441 " thousand",
2442 " million",
2443 " billion",
2444 " trillion",
2445 " quadrillion",
2446 " quintillion",
2447 " sextillion",
2448 " septillion",
2449 " octillion",
2450 " nonillion",
2451 " decillion"
2452 ]
2453 .iter()
2454 .map(|s| s.to_string())
2455 .collect();
2456}
2457
2458