0

I want write a program that accepts an integer between 1 and 9999 (inclusive) and prints the value in words. For example, if the user enters:

3421

then the program should print:

three thousand four hundred twenty one

My code is below, but it doesn't work.

num=int(input('please enter an integer between 1 and 9999: '))

def int_to_en(num):
    d = { 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', 14 : 'fourteen', \
          15 : 'fifteen', 16 : 'sixteen', 17 : 'seventeen', 18 : 'eighteen', \
          19 : 'ninteen', 20 : 'twenty', \
          30 : 'thirty', 40 : 'fourth', 50 : 'fifty', 60 : 'sixty', \
          70 : 'seventy', 80 : 'eighty', 90 : 'ninty' }
    k = 1000
    m = k * 1000

    if (num < 20):
        print(d[num])

    if (num < 100):
        if num % 10 == 0:
            print(d[num])
        else:
            print(d[num // 10 * 10] + '' + d[num % 10])

    if (num < k):
        if num % 100 == 0:
            print(d[num // 100] + ' hundred')
        else:
            print(d[num // 100] + ' hundred ' + int_to_en(num % 100))

    if (num < m):
        if num % k == 0:
            print(int_to_en(num // k) + ' thousand')
        else:
            print(int_to_en(num // k) + ' thousand, ' + int_to_en(num % k))
Prune
  • 76,765
  • 14
  • 60
  • 81
iSam
  • 55
  • 1
  • 1
  • 8
  • 2
    What specifically is not working? – C_Z_ Feb 15 '16 at 18:37
  • I think the code formatting got messed up between your original post (no formatting at all) and @CactusWoman's edit. Are these ``if`` really inside the function? – MSeifert Feb 15 '16 at 18:40
  • There is no initial call for `int_to_en` – Forge Feb 15 '16 at 18:42
  • You're never returning anything, so you can't use recursion. – Morgan Thrapp Feb 15 '16 at 18:42
  • Actually, he *can* use recursion. The program prints successive values instead of passing the translations back up the line. – Prune Feb 15 '16 at 18:49
  • @CactusWoman You can run it in your system. That's had no error but no output!? – iSam Feb 15 '16 at 18:52
  • As others pointed out, it has no errors and no output because you never call the function from your main program. – Prune Feb 15 '16 at 18:53
  • Can any body edit my code, I don't know, that is true of false. I need write a program for print a word from my integer between 1 and 9999 as upper structure and no other structure! – iSam Feb 15 '16 at 18:56
  • @Prune Can you edit it for call or work without function? – iSam Feb 15 '16 at 18:57
  • 1
    StackOverflow is not a coding or tutorial service. When you clarify your problem statement, we need you to put the extra information into the main body of the question -- not in a comment below. – Prune Feb 15 '16 at 19:13

3 Answers3

2

I created such a function before. It's not perfect, but it works pretty well:

def word_form(number):
    """word_form(number) -> string

    Returns the word form of the number.
    >>> word_form(32)
    'thirty-two'
    >>> word_form(123)
    'one hundred twenty-three'
    The highest number it is capable of converting is:
        999,999,999,999,999,999,999,999,999,999,999"""

    ones = ("", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine")
    tens = ("", "", "twenty", "thirty", "forty", "fifty", "sixty", "seventy", "eighty", "ninety")
    teens = ("ten", "eleven", "twelve", "thirteen", "fourteen", "fifteen", "sixteen", "seventeen", "eighteen", "nineteen")
    levels = ("", "thousand", "million", "billion", "trillion", "quadrillion", "quintillion", "sextillion", "septillion", "octillion", "nonillion")

    word = ""
    #number will now be the reverse of the string form of itself.
    num = reversed(str(number))
    number = ""
    for x in num:
        number += x
    del num
    if len(number) % 3 == 1: number += "0"
    x = 0
    for digit in number:
        if x % 3 == 0:
            word = levels[x / 3] + ", " + word
            n = int(digit)
        elif x % 3 == 1:
            if digit == "1":
                num = teens[n]
            else:
                num = tens[int(digit)]
                if n:
                    if num:
                        num += "-" + ones[n]
                    else:
                        num = ones[n]
            word = num + " " + word
        elif x % 3 == 2:
            if digit != "0":
                word = ones[int(digit)] + " hundred " + word
        x += 1
    return word.strip(", ")

Usage example:

word_form(1)
>>> 'one'

word_form(999)
>>> 'nine hundred ninety-nine'
dot.Py
  • 5,007
  • 5
  • 31
  • 52
zondo
  • 19,901
  • 8
  • 44
  • 83
  • thanks a lot but I just write with this structure, that I wrote (without del, str and ...). Thanks. – iSam Feb 15 '16 at 19:08
2

The return value for int_to_en is None, that will fail the concatenation in your code, try to return String instead and concatenate the result then.

num=int(input('please enter an integer between 1 and 9999: '))

def int_to_en(num):
    d = { 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', 14 : 'fourteen', \
          15 : 'fifteen', 16 : 'sixteen', 17 : 'seventeen', 18 : 'eighteen', \
          19 : 'ninteen', 20 : 'twenty', \
          30 : 'thirty', 40 : 'fourth', 50 : 'fifty', 60 : 'sixty', \
          70 : 'seventy', 80 : 'eighty', 90 : 'ninty' }
    k = 1000
    m = k * 1000

    if (num < 20):
        return d[num]

    if (num < 100):
        if num % 10 == 0:
            return d[num]
        else:
            return d[num // 10 * 10] + ' ' + d[num % 10]

    if (num < k):
        if num % 100 == 0:
            return d[num // 100] + ' hundred'
        else:
            return d[num // 100] + ' hundred ' + int_to_en(num % 100)
    if (num < m):
        if num % k == 0:
            return int_to_en(num // k) + ' thousand'
        else:
            return int_to_en(num // k) + ' thousand, ' + int_to_en(num % k)

print int_to_en(num)
Forge
  • 6,538
  • 6
  • 44
  • 64
  • Thanks. But when I use for example 55, output is 55 times fiftyfive! So I need only one fiftyfive! I think I need break between if, right? – iSam Feb 15 '16 at 19:06
  • Yes, you need to add a missing space. Take a look at the corrected code above. – Forge Feb 15 '16 at 19:09
0

Once you bother to call the function, the next problem you hit is that your if statements are not exclusive. For instance, with an input of only 5 ... You see that 5 < 20. You print "five". You go to the next if statement. Sure enough, 5 < 100. You process the number as larger ... and go into an infinite recursion.

You have to make sure that you execute only one of those if statements. For all but the first, use elif instead of if.


To get past your None problem, you can appropriately change your print statements to return statements. Don't print anything until you get back to the main program; the other calls simply append the results as you figure them out, and the main program gets the whole string to print at once.


To save yourself a lot of time, please learn basic debugging.

Prune
  • 76,765
  • 14
  • 60
  • 81
  • I corrected but till 99 write for example nintynine and in next line None! and when I write more than 99, show me like bellow error: Traceback (most recent call last): File "/Users/iSam/Desktop/number_to_word.py", line 29, in print(int_to_en(num), end = "") File "/Users/iSam/Desktop/number_to_word.py", line 23, in int_to_en print(d[num//100]+' hundred '+int_to_en(num%100)) TypeError: Can't convert 'NoneType' object to str implicitly – iSam Feb 15 '16 at 19:30
  • This is exactly the problem that others have pointed out: you return **None** from your function. When you return from a recursive call and try to concatenate the **None** to "hundred", you get an error. – Prune Feb 15 '16 at 19:33
  • Please make the changes we've suggested. If you have a new problem after that and cannot solve it, please post a new question. We've already fixed three problems in this one; StackOverflow is supposed to be one problem per posting. – Prune Feb 15 '16 at 19:34
  • Thanks, but I just use print and not return. – iSam Feb 15 '16 at 20:10