From f77d5a95e78b64208b548cecd006f590a4341488 Mon Sep 17 00:00:00 2001 From: Dmitry Kokorin Date: Fri, 8 Apr 2016 14:12:40 +0300 Subject: [PATCH] say: passes tests --- cpp/say/say.cpp | 95 +++++++++++++++++++++++-------------------------- cpp/say/say.h | 2 +- 2 files changed, 46 insertions(+), 51 deletions(-) diff --git a/cpp/say/say.cpp b/cpp/say/say.cpp index 44e2262..06e497f 100644 --- a/cpp/say/say.cpp +++ b/cpp/say/say.cpp @@ -1,8 +1,8 @@ #include "say.h" +#include #include -#include namespace say { @@ -10,75 +10,70 @@ using namespace std; namespace { -const unordered_map numbers_map = { - {0, "zero"}, - {1, "one"}, - {2, "two"}, - {3, "three"}, - {4, "four"}, - {5, "five"}, - {6, "six"}, - {7, "seven"}, - {8, "eight"}, - {9, "nine"}, +const unordered_map number_map = { + {0, "zero"}, + {1, "one"}, + {2, "two"}, + {3, "three"}, + {4, "four"}, + {5, "five"}, + {6, "six"}, + {7, "seven"}, + {8, "eight"}, + {9, "nine"}, {10, "ten"}, {11, "eleven"}, {12, "twelve"}, {13, "thirteen"}, {20, "twenty"}, {30, "thirty"}, + {40, "forty"}, {50, "fifty"}, {80, "eighty"} }; + +struct order_t +{ + number_t divisor; + number_t max; + string separator; + string suffix; +}; + +const order_t orders[] = { + {10, 100, "-", "ty"}, + {100, 1000, " ", " hundred"}, + {1000, 1000000, " ", " thousand"}, + {1000000, 1000000000, " ", " million"}, + {1000000000, 1000000000000, " ", " billion"} +}; + } string in_english(number_t number) { + if (number_map.count(number)) + return number_map.at(number); + if (number > 13 && number < 20) - return numbers_map.at(number - 10) + "teen"; + return number_map.at(number - 10) + "teen"; - if (number >= 20 && number < 100 && (number % 10 == 0)) { + for (auto o : orders) { - if (numbers_map.count(number)) - return numbers_map.at(number); + if (number >= o.divisor && number < o.max) { - return numbers_map.at(number / 10) + "ty"; + if (number % o.divisor == 0) + return in_english(number / o.divisor) + o.suffix; + + number_t reminder = number % o.divisor; + number_t div_part = number - reminder; + + return in_english(div_part) + o.separator + in_english(reminder); + } } - if (number > 20 && number < 100) { - - number_t ones = number % 10; - number_t tens = number - ones; - - return in_english(tens) + '-' + in_english(ones); - } - - if (number >= 100 && number < 1000) { - - if (number % 100 == 0) - return in_english(number / 100) + " hundred"; - - number_t rest = number % 100; - number_t hundreds = number - rest; - - return in_english(hundreds) + ' ' + in_english(rest); - } - - if (number >= 1000 && number < 1000000) { - - cout << number << endl; - - if (number % 1000 == 0) - return in_english(number / 1000) + " thousand"; - - number_t rest = number % 1000; - number_t thousands = number - rest; - - return in_english(thousands) + ' ' + in_english(rest); - } - - return numbers_map.at(number); + throw domain_error("can't say the number"); } diff --git a/cpp/say/say.h b/cpp/say/say.h index 99f9987..3251407 100644 --- a/cpp/say/say.h +++ b/cpp/say/say.h @@ -6,7 +6,7 @@ namespace say { -typedef unsigned long long number_t; +typedef long long number_t; std::string in_english(number_t number);