korean_nums/
numbers.rs

1use num::{FromPrimitive, Integer};
2
3use crate::errors::HangeulError;
4use crate::parse;
5
6pub enum NumberSystem {
7    PureKorean,
8    SinoKorean,
9}
10
11pub struct KoreanInteger<I>
12where
13    I: Copy + ToString + Integer + FromPrimitive,
14{
15    pub value: I,
16    pub num_system: NumberSystem,
17}
18
19impl<I> KoreanInteger<I>
20where
21    I: Copy + ToString + Integer + FromPrimitive,
22{
23    pub fn from_int(value: I, num_system: NumberSystem) -> KoreanInteger<I> {
24        let integer = KoreanInteger {
25            value: value,
26            num_system,
27        };
28
29        integer.validate();
30        integer
31    }
32
33    pub fn validate(&self) {
34        match self.num_system {
35            NumberSystem::PureKorean => {
36                if self.value > FromPrimitive::from_i8(99).unwrap() {
37                    panic!("Pure korean numbers only go up to 99.");
38                }
39                if self.value < FromPrimitive::from_i8(1).unwrap() {
40                    panic!("Input cannot be 0 or negative.")
41                }
42            }
43            NumberSystem::SinoKorean => {}
44        }
45    }
46
47    pub fn get_hangeul(&self) -> Result<String, HangeulError> {
48        let prepared_input = self.prepare_input();
49
50        match self.num_system {
51            NumberSystem::PureKorean => parse::parse_hangeul_pure(prepared_input),
52            NumberSystem::SinoKorean => parse::parse_hangeul_sino(prepared_input),
53        }
54    }
55
56    fn prepare_input(&self) -> Vec<char> {
57        let nums = self
58            .value
59            .to_string()
60            .replace(",", "")
61            .chars()
62            .rev()
63            .collect();
64
65        nums
66    }
67}
68
69pub enum KoreanNumberSino {
70    Zero,
71    One,
72    Two,
73    Three,
74    Four,
75    Five,
76    Six,
77    Seven,
78    Eight,
79    Nine,
80}
81
82#[allow(dead_code)]
83pub enum EndingType {
84    Vowel,
85    Consonant,
86}
87
88#[allow(dead_code)]
89impl EndingType {
90    pub fn subject_particle(&self) -> &str {
91        match self {
92            &EndingType::Vowel => "가",
93            &EndingType::Consonant => "이",
94        }
95    }
96
97    pub fn topic_particle(&self) -> &str {
98        match self {
99            &EndingType::Vowel => "는",
100            &EndingType::Consonant => "은",
101        }
102    }
103}
104
105impl PartialEq<i8> for KoreanNumberSino {
106    fn eq(&self, other: &i8) -> bool {
107        self.to_i8().eq(other)
108    }
109}
110
111impl KoreanNumberSino {
112    pub fn from_char(c: &char) -> Option<KoreanNumberSino> {
113        match c {
114            '0' => Some(KoreanNumberSino::Zero),
115            '1' => Some(KoreanNumberSino::One),
116            '2' => Some(KoreanNumberSino::Two),
117            '3' => Some(KoreanNumberSino::Three),
118            '4' => Some(KoreanNumberSino::Four),
119            '5' => Some(KoreanNumberSino::Five),
120            '6' => Some(KoreanNumberSino::Six),
121            '7' => Some(KoreanNumberSino::Seven),
122            '8' => Some(KoreanNumberSino::Eight),
123            '9' => Some(KoreanNumberSino::Nine),
124            _ => None,
125        }
126    }
127
128    pub fn to_str(&self) -> &str {
129        match self {
130            &KoreanNumberSino::Zero => "",
131            &KoreanNumberSino::One => "일",
132            &KoreanNumberSino::Two => "이",
133            &KoreanNumberSino::Three => "삼",
134            &KoreanNumberSino::Four => "사",
135            &KoreanNumberSino::Five => "오",
136            &KoreanNumberSino::Six => "육",
137            &KoreanNumberSino::Seven => "칠",
138            &KoreanNumberSino::Eight => "팔",
139            &KoreanNumberSino::Nine => "구",
140        }
141    }
142
143    pub fn to_i8(&self) -> i8 {
144        match self {
145            &KoreanNumberSino::Zero => 0,
146            &KoreanNumberSino::One => 1,
147            &KoreanNumberSino::Two => 2,
148            &KoreanNumberSino::Three => 3,
149            &KoreanNumberSino::Four => 4,
150            &KoreanNumberSino::Five => 5,
151            &KoreanNumberSino::Six => 6,
152            &KoreanNumberSino::Seven => 7,
153            &KoreanNumberSino::Eight => 8,
154            &KoreanNumberSino::Nine => 9,
155        }
156    }
157
158    #[allow(dead_code)]
159    pub fn ending_type(&self) -> EndingType {
160        match self {
161            &KoreanNumberSino::Zero => EndingType::Consonant,
162            &KoreanNumberSino::One => EndingType::Consonant,
163            &KoreanNumberSino::Two => EndingType::Vowel,
164            &KoreanNumberSino::Three => EndingType::Consonant,
165            &KoreanNumberSino::Four => EndingType::Vowel,
166            &KoreanNumberSino::Five => EndingType::Vowel,
167            &KoreanNumberSino::Six => EndingType::Consonant,
168            &KoreanNumberSino::Seven => EndingType::Consonant,
169            &KoreanNumberSino::Eight => EndingType::Consonant,
170            &KoreanNumberSino::Nine => EndingType::Vowel,
171            //&KoreanNumberSino::Ten    => EndingType::Consonant,
172        }
173    }
174
175    #[allow(dead_code)]
176    pub fn to_hanja(&self) -> &str {
177        match self {
178            &KoreanNumberSino::Zero => "零/〇",
179            &KoreanNumberSino::One => "一",
180            &KoreanNumberSino::Two => "二",
181            &KoreanNumberSino::Three => "三",
182            &KoreanNumberSino::Four => "四",
183            &KoreanNumberSino::Five => "五",
184            &KoreanNumberSino::Six => "六",
185            &KoreanNumberSino::Seven => "七",
186            &KoreanNumberSino::Eight => "八",
187            &KoreanNumberSino::Nine => "九",
188            //&KoreanNumberSino::Ten => "十",
189        }
190    }
191}
192
193pub enum KoreanNumberPure {
194    One,
195    Two,
196    Three,
197    Four,
198    Five,
199    Six,
200    Seven,
201    Eight,
202    Nine,
203    Ten,
204    Twenty,
205    Thirty,
206    Forty,
207    Fifty,
208    Sixty,
209    Seventy,
210    Eighty,
211    Ninety,
212}
213
214impl KoreanNumberPure {
215    pub fn from_char(c: &char) -> Option<KoreanNumberPure> {
216        match c {
217            '1' => Some(KoreanNumberPure::One),
218            '2' => Some(KoreanNumberPure::Two),
219            '3' => Some(KoreanNumberPure::Three),
220            '4' => Some(KoreanNumberPure::Four),
221            '5' => Some(KoreanNumberPure::Five),
222            '6' => Some(KoreanNumberPure::Six),
223            '7' => Some(KoreanNumberPure::Seven),
224            '8' => Some(KoreanNumberPure::Eight),
225            '9' => Some(KoreanNumberPure::Nine),
226            _ => None,
227        }
228    }
229
230    pub fn from_str(s: &str) -> Option<KoreanNumberPure> {
231        match s {
232            "10" => Some(KoreanNumberPure::Ten),
233            "20" => Some(KoreanNumberPure::Twenty),
234            "30" => Some(KoreanNumberPure::Thirty),
235            "40" => Some(KoreanNumberPure::Forty),
236            "50" => Some(KoreanNumberPure::Fifty),
237            "60" => Some(KoreanNumberPure::Sixty),
238            "70" => Some(KoreanNumberPure::Seventy),
239            "80" => Some(KoreanNumberPure::Eighty),
240            "90" => Some(KoreanNumberPure::Ninety),
241            _ => None,
242        }
243    }
244
245    pub fn to_str(&self) -> &str {
246        match self {
247            &KoreanNumberPure::One => "하나",
248            &KoreanNumberPure::Two => "둘",
249            &KoreanNumberPure::Three => "셋",
250            &KoreanNumberPure::Four => "넷",
251            &KoreanNumberPure::Five => "다섯",
252            &KoreanNumberPure::Six => "여섯",
253            &KoreanNumberPure::Seven => "일곱",
254            &KoreanNumberPure::Eight => "여덟",
255            &KoreanNumberPure::Nine => "아홉",
256            &KoreanNumberPure::Ten => "열",
257            &KoreanNumberPure::Twenty => "스물",
258            &KoreanNumberPure::Thirty => "서른",
259            &KoreanNumberPure::Forty => "마흔",
260            &KoreanNumberPure::Fifty => "쉰",
261            &KoreanNumberPure::Sixty => "예순",
262            &KoreanNumberPure::Seventy => "일흔",
263            &KoreanNumberPure::Eighty => "여든",
264            &KoreanNumberPure::Ninety => "아흔",
265        }
266    }
267}