Skip to content

Instantly share code, notes, and snippets.

@dmrz
Last active December 20, 2015 19:49
Show Gist options
  • Save dmrz/6186342 to your computer and use it in GitHub Desktop.
Save dmrz/6186342 to your computer and use it in GitHub Desktop.
#!/usr/bin/env python
import re
import sys
import unittest
NUMBERS = {
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',
14: 'fourteen',
15: 'fifteen',
16: 'sixteen',
17: 'seventeen',
18: 'eighteen',
19: 'nineteen',
20: 'twenty',
30: 'thirty',
40: 'forty',
50: 'fifty',
60: 'sixty',
70: 'seventy',
80: 'eighty',
90: 'ninety'
}
get_first_digit = lambda number: int(str(number)[0])
get_rest = lambda number: int(str(number)[1:])
s_if_plural = lambda first_digit, use_plural: 's' if use_plural and first_digit > 1 else ''
ten = '{0}-{1}'
hundred = '{0} hundred{1}'
hundred_remainder = '{0} and {1}'
thousand = '{0} thousand{1}'
thousand_remainder = '{0} {1}'
def get_number_name(number, use_plural=False):
first_digit = get_first_digit(number)
if number in NUMBERS:
return NUMBERS[number]
elif 100 > number > 20:
return ten.format(
get_number_name(first_digit * 10, use_plural),
get_number_name(get_rest(number), use_plural)
)
elif int(1e3) > number >= 100:
if not (number % 100):
return hundred.format(
get_number_name(first_digit, use_plural),
s_if_plural(first_digit, use_plural)
)
else:
return hundred_remainder.format(
get_number_name(first_digit * 100, use_plural),
get_number_name(get_rest(number), use_plural)
)
elif int(1e6) > number >= int(1e3):
if not (number % int(1e3)):
return thousand.format(
get_number_name(first_digit, use_plural),
s_if_plural(first_digit, use_plural)
)
else:
return thousand_remainder.format(
get_number_name(first_digit * int(1e3), use_plural),
get_number_name(get_rest(number), use_plural)
)
def get_letter_count(number, use_plural=False):
number_name = get_number_name(number, use_plural)
return len(re.sub(r'[- ]', '', number_name))
def get_number_letter_counts(start, end, use_plural=False):
return sum(get_letter_count(x, use_plural) for x in range(start, end + 1))
class TestHelpers(unittest.TestCase):
def test_get_letter_count(self):
self.assertEqual(get_letter_count(342), 23)
self.assertEqual(get_letter_count(342, use_plural=True), 24)
self.assertEqual(get_letter_count(115), 20)
def test_get_number_letter_counts(self):
self.assertEqual(get_number_letter_counts(1, 5), 19)
if __name__ == '__main__':
if len(sys.argv) == 2 and sys.argv[1] == 'test':
sys.argv.pop()
unittest.main()
else:
result = get_number_letter_counts(1, 1000)
print(result)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment