noob question Letters in words?

Steven D'Aprano steve at REMOVETHIScyber.com.au
Fri Oct 7 22:35:27 EDT 2005


On Fri, 07 Oct 2005 20:46:39 -0400, Ivan Shevanski wrote:

> Alright heres another noob question for everyone.  Alright, say I have a 
> menu like this.
> 
> print "1. . .Start"
> print "2. . .End"
> choice1 = raw_input("> ")
> 
> and then I had this to determine what option.

Firstly, you need to decide on what you want to accept. If you really do
want to (I quote from later in your post) 

> For instance I could type in Stop and would get the first option since
> it had an "s" in it?

then you can, but that would be a BAD idea!!! 

py> run_dangerous_code()
WARNING! This will erase all your data if you continue!
Are you sure you want to start? Yes/Start/Begin
> Stop
Starting now... data erased.

Oh yeah, your users will love you for that.

I could handle it like this:

def yesno(s):
    """Returns a three-valued flag based on string s.
    The flag is 1 for "go ahead", 0 for "don't go" 
    and -1 for any other unrecognised response.
    Recognises lots of different synonyms for yes and no.
    """
    s = s.strip().lower()  # case and whitespace doesn't matter
    if s in ('1', 'start', 's', 'begin', 'ok', 'okay', 'yes'):
        return 1
    elif s in ('2', 'end', 'e', 'cancel', 'c', 'stop', 'no'):
        return 0
    else:
        return -1


def query():
    print "Start process: 1 start"
    print "End process: 2 end"
    raw_choice = raw_input("> ")
    choice = yesno(raw_choice)
    if choice == -1:
        print "I'm sorry, I don't understand your response."
        return query()
    else:
        return choice


But that's probably confusing. Why do you need to offer so many ways of
answering the question? Generally, the best way of doing this sort of
thing is:

- give only one way of saying "go ahead", which is usually "yes".
- give only one way of saying "don't go ahead", which is usually "no".
- if the thing you are doing is not dangerous, allow a simple return to
do the same as the default.
- if, and only if, the two choices are unambiguous, allow the first
letter on its own (e.g. "y" or "n") to mean the same as the entire word.

Using this simpler method:

def yesno(s):
    s = s.strip().lower()
    if s in ('yes', 'y'):
        return 1
    elif s in ('no', 'n'):
        return 0
    else:
        return -1

def query:
    print "Start process? (y/n)"
    choice = yesno(raw_choice("> "))
    if choice == -1:
        print "Please type Yes or No."
        return query()
    else:
        return choice


Hope this is helpful.


-- 
Steven.




More information about the Python-list mailing list