숫자를 영어 단어로 변환하는 알고리즘
이 알고리즘은 주어진 숫자를 그에 대응하는 영어 단어로 변환합니다. 예를 들어 564를 입력하면 Five Hundred and Sixty-Four라는 결과를 얻습니다.
변환 과정에서는 숫자 범위별로 미리 정의된 문자열 목록을 활용합니다. 알고리즘은 입력값의 크기를 판단해 목록에서 알맞은 단어를 꺼내고, 필요하면 재귀 호출을 통해 나머지 자릿수를 계속 처리하여 최종 문장을 완성합니다.
미리 정의된 문자열 목록
- Units(일의 자리): 0~9에 해당하는 단어를 저장합니다. (Zero, One, ... Nine)
- twoDigits(10~19): 규칙적이지 않은 두 자리 수 단어를 저장합니다. (Ten, Eleven, ... Nineteen)
- tenMul(십의 자리): 20~90 사이의 십의 배수 단어를 저장합니다. (Twenty, Thirty, ... Ninety)
- tenPower(10의 거듭제곱): Hundred(백, 10의 2제곱)와 Thousand(천, 10의 3제곱)을 저장합니다.
입력 및 출력
입력: 568 출력: Five Hundred And Sixty Eight
알고리즘 설계
함수는 numToWord(num) 형태로 정의하며, 정수 범위별 단어를 담은 목록들을 참조해 동작합니다.
- 입력: 변환할 숫자
- 출력: 숫자에 대응하는 영어 단어
Begin
if n ≥ 0 and n < 10, then
display units(n) into words // 일의 자리
else if n ≥ 10 and n < 20, then
display twoDigitNum(n) into words // 10~19 구간
else if n ≥ 20 and n < 100, then
display tensMultiple(n/10) into words // 십의 자리 출력
if n mod 10 ≠ 0, then
numToWord(n mod 10) // 일의 자리 재귀 처리
else if n ≥ 100 and n < 1000, then
display units(n/100) into words // 백의 자리 숫자
display "Hundred"
if n mod 100 ≠ 0, then
display "And"
numToWord(n mod 100)
else if n ≥ 1000 and n ≤ 32767, then
numToWord(n/1000) // 천의 자리 먼저 변환
display "Thousand"
if n mod 1000 ≠ 0, then
numToWord(n mod 1000)
else
display invalid number and exit // 유효하지 않은 입력
End
C++ 구현 예제
#include<iostream>
using namespace std;
// 한 자리 숫자(0~9)를 단어로 반환
string getUnit(int n) {
string unit[10] = {"Zero", "One", "Two", "Three", "Four", "Five", "Six", "Seven", "Eight", "Nine"};
return unit[n];
}
// 두 자리 수(10~19)를 단어로 반환
string getTwoDigits(int n) {
string td[10] = {"Ten", "Eleven", "Twelve", "Thirteen", "Fourteen", "Fifteen", "Sixteen", "Seventeen", "Eighteen", "Nineteen"};
return td[n % 10];
}
// 십의 배수(20~90)를 단어로 반환
string getTenMul(int n) {
string tm[8] = {"Twenty", "Thirty", "Forty", "Fifty", "Sixty", "Seventy", "Eighty", "Ninety"};
return tm[n - 2];
}
// 10의 거듭제곱(Hundred, Thousand)을 단어로 반환
string getTenPow(int pow) {
string power[2] = {"Hundred", "Thousand"};
return power[pow - 2];
}
void printNumToWord(int n) {
if (n >= 0 && n < 10)
cout << getUnit(n) << " "; // 일의 자리 출력
else if (n >= 10 && n < 20)
cout << getTwoDigits(n) << " "; // 11~19 처리
else if (n >= 20 && n < 100) {
cout << getTenMul(n / 10) << " ";
if (n % 10 != 0)
printNumToWord(n % 10); // 재귀 호출로 나머지 처리
} else if (n >= 100 && n < 1000) {
cout << getUnit(n / 100) << " ";
cout << getTenPow(2) << " ";
if (n % 100 != 0) {
cout << "And ";
printNumToWord(n % 100);
}
} else if (n >= 1000 && n <= 32767) {
printNumToWord(n / 1000);
cout << getTenPow(3) << " ";
if (n % 1000 != 0)
printNumToWord(n % 1000);
} else
printf("Invalid Input"); // 유효 범위 초과
}
main() {
int number;
cout << "Enter a number between 0 to 32767: ";
cin >> number;
printNumToWord(number);
}
실행 결과
Enter a number between 0 to 32767: 568 Five Hundred And Sixty Eight
정리
이 알고리즘의 핵심은 자릿수별로 문자열 목록을 분류해 두고, 큰 자릿수부터 몫과 나머지를 이용해 재귀적으로 처리하는 것입니다. 이 구조를 확장하면 Million, Billion처럼 더 큰 단위도 손쉽게 지원할 수 있습니다. 참고로 원본 코드의 "Fourty", "Ninty"는 올바른 철자인 "Forty", "Ninety"로 수정했습니다.