How to check if a user input is a float

pez picture pez · Apr 26, 2014 · Viewed 17.4k times · Source

I'm doing Learn Python the Hard Way exercise 35. Below is the original code, and we're asked to change it so it can accept numbers that don't have just 0 and 1 in them.

def gold_room():
    print "This room is full of gold. How much do you take?"

    next = raw_input("> ")

    if "0" in next or "1" in next:
        how_much = int(next)

    else:
        dead("Man, learn to type a number.")

    if how_much < 50:
        print "Nice, you're not greedy, you win!"
        exit(0)

    else:
        dead("You greedy bastard!")

This is my solution, which runs fine and recognizes float values:

def gold_room():
    print "This room is full of gold. What percent of it do you take?"

    next = raw_input("> ")

    try:
        how_much = float(next)
    except ValueError:
        print "Man, learn to type a number."
        gold_room()

    if how_much <= 50:
        print "Nice, you're not greedy, you win!"
        exit(0)

    else:
        dead("You greedy bastard!")

Searching through similar questions, I found some answers that helped me write another solution, shown in the below code. The problem is, using isdigit() doesn't let the user put in a float value. So if the user said they want to take 50.5%, it would tell them to learn how to type a number. It works otherwise for integers. How can I get around this?

def gold_room():
    print "This room is full of gold. What percent of it do you take?"

    next = raw_input("> ")

while True:
    if next.isdigit():
        how_much = float(next)

        if how_much <= 50:
            print "Nice, you're not greedy, you win!"
            exit(0)

        else:
            dead("You greedy bastard!")

    else: 
        print "Man, learn to type a number."
        gold_room()

Answer

cdhagmann picture cdhagmann · Apr 26, 2014

isinstance(next, (float, int)) will do the trick simply if next is already converted from a string. It isn't in this case. As such you would have to use re to do the conversion if you want to avoid using try..except.

I would recommend using the try..except block that you had before instead of a if..else block, but putting more of the code inside, as shown below.

def gold_room():
    while True:
        print "This room is full of gold. What percent of it do you take?"
        try:
            how_much = float(raw_input("> "))

            if how_much <= 50:
                print "Nice, you're not greedy, you win!"
                exit(0)

            else:
                dead("You greedy bastard!")

        except ValueError: 
            print "Man, learn to type a number."

This will try to cast it as a float and if it fails will raise a ValueError that will be caught. To learn more, see the Python Tutorial on it.