Python:用用户输入的字符替换星号(猜单词游戏)

0 投票
3 回答
4122 浏览
提问于 2025-04-17 13:40

我一直在尝试为我的计算机课编写一个猜单词游戏,但遇到了一些困难。

这个程序基本上是让用户输入一个单词,然后它会运行一个循环,生成一个和输入单词长度一样的星号字符串。

当用户输入一个正确的字母时,程序会把对应位置的星号替换成这个字母,保持顺序。例如,如果单词是“lie”,用户输入“i”,那么程序会把“*”变成“i”。

下面是代码。

def guess_part(word):
    lives = 6
    LetterCount = 0
    LetterMask = ""
    for x in range(len(word)):
        LetterMask = LetterMask + "*"
    print LetterMask
    while lives != 0 and LetterMask.find("*")!=-1:
        LetterGuess = raw_input("Enter a letter to guess?")
        LetterCount = 0
        for char in word:
            LetterCount = LetterCount + 1
            if LetterGuess == char:
                print "Good Guess."
                LetterMask = LetterMask.replace(LetterMask[LetterCount], LetterGuess)
                print LetterMask

def rand_word():
    from random import randrange #import the randrange function, from "random"
    random_words = ['extraordinary','happy','computer','python','screen','cheese','cabaret','caravan','bee','wasp','insect','mitosis','electronegativity','jumper','trousers'] #list of different words which can be used by the program for the end user to guess.
    word = random_words[randrange(0, 15)] #pick a random number, and use this number as an index for the list, "random_words".
    guess_part(word) #call the function, "guess_part" with the parameter "word"

def user_word():
    print "All words will be changed to lowercase."
    print "Enter the word you would like to guess."
    print ""
    validation_input = False #Setting the validation unput to "False"
    while validation_input == False: #while the validation input is not False, do below.
        word = raw_input("") #Ask for input, and set the value to the variable, "word".
        if word.isalpha(): #If word contains only strings, no numbers or symbols, do below.
            word = word.lower() #set the string of variable, "word", to all lowercase letters.
            guess_part(word) #call the function, "guess_part" with the parameter, "word".
            validation_input = True #Break the while loop - set validation_input to "False".
        else: #if the above isn't met, do the below.
            print "Word either contained numbers or symbols."

def menu():
    print "Hangman Game"
    print ""
    print "Ashley Collinge"
    print ""
    print "You will have 6 lives. Everytime you incorrectly guess a word, you will lose a life."
    print "The score at the end of the game, is used to determine the winner."
    print ""
    print "Would you like to use a randomly generated word, or input your own?"
    print "Enter 'R' for randomly generated word, or 'I' for your own input."
    decision_bool = False #Set the decision_bool to "False".
    decision_length = False #Set the decision_length to "False".
    while decision_bool == False: #While decision_bool equals "False", do below.
        decision = raw_input("") #Ask for input, value set to the variable "decision".
        while decision_length == False: #While decision_length equals "False", do below.
            if len(decision) == 1: #If the length of decision eqausl 1, do below.
                decision_length = True #Set decision_length to "True."
                decision = decision.capitalize() #Capitalize the string value of decision.
                if decision == "R": #if the value of decision, eqauls "R".
                    print "You chose randomly generated word."
                    print ""
                    print "Forwarding..."
                    decision_bool = True #Set decision_bool to "True".
                    print ""
                    rand_word() #Call the function, rand_word()
                elif decision =="I": #If decision equals "I", do below.
                    print "You chose to input your own word."
                    print ""
                    print "Forwarding..."
                    decision_bool = True #Set decision_bool to "False".
                    print ""
                    user_word() #Call the function, user_word()
                else:
                    print "You entered an incorrect value for the question. Try again."
            else:
                print "You entered an incorrect value for the question. Try again."

menu()

我已经对大部分代码进行了注释,但如果有不太清楚的地方,我会回答。

3 个回答

0

我猜你遇到的问题是在 guess_part() 这个函数上,这里有一个可以正常工作的版本:

def guess_part(word):
    lives = 6
    # Make a mutable array of characters same length as word
    LetterMask = bytearray("*" * len(word))
    while lives > 0 and LetterMask != word:
        print LetterMask
        while True:
            LetterGuess = raw_input("Enter a letter to guess: ")
            if LetterGuess: break
        LetterGuess = LetterGuess[0] # only take first char if more than one
        if LetterGuess in LetterMask:
            print "Sorry, you already guessed that letter. Try again."
            countinue
        GoodGuess = False
        for i, char in enumerate(word):
            if char == LetterGuess:
                GoodGuess = True
                LetterMask[i] = char
        if GoodGuess:
            print "Good guess."
        else:
            print "Sorry, bad guess"
            lives -= 1
    GuessedWholeWord = LetterMask == word
    if GuessedWholeWord:
        print "Congratulations, you guessed the whole word!"
    else:
        print "Sorry, no more guesses. You're hanged!"
    return GuessedWholeWord
1

你已经很接近了,但还差一点。这里有几个提示:

1) 你需要在 guess_part() 这个函数里减少 lives 的值。

2) 这个:

LetterMask = LetterMask.replace(LetterMask[LetterCount], LetterGuess)

并没有按照你想要的那样工作。我建议你用一个简单的替代方案,比如:

LetterMask = list(LetterMask)
LetterMask[LetterCount-1] = LetterGuess
LetterMask = "".join(LetterMask)

3) 另外注意一下(上面提到的)字母计数中的“-1”,因为字符串是从0开始计数的,所以你少了一位。

只要做这几个小调整,你就差不多可以了。

2

我不会把你的整个程序写出来,但简单来说:

假设 word 是一个单词(比如 word = 'liar')。我们需要一个函数,它可以把一个单词和一组猜测的字母转换成一个由星号和已经猜过的字母组成的字符串。

def asterisker(word, guesses=[]):
    result = ""
    for letter in word:
        result += letter if letter in guesses else "*"
        # which does what the below does:
        # if letter in guesses:
        #     result += letter
        # else:
        #     result += "*"
    return result

这样就能得到:

In [4]: asterisker("liar")
Out[4]: '****'

In [7]: asterisker("liar", ["l", "r" ])
Out[7]: 'l**r'

我可能会这样写,虽然上面的原始代码可能更好或更清晰。

def asterisker(word, guesses=[]):
    return "".join(l if l in guesses else "*" for l in word)

补充一下,正如Mike提到的(第一个),如果有人猜错了,你确实需要减少"lives"的数量。


另外,这里有一些在写Python时可以用的小建议。

1) 不要使用大写的变量名(比如 LetterMask);如果你想让它看起来像两个词,可以用 lettermaskletter_mask

2) 像"validation_input = False #Setting the validation input to "False""这样的注释没有什么帮助,反而让代码显得杂乱。你把变量设置为False,这一点代码已经很清楚了。在你做的事情不太明确的情况下,注释可能更有用。其实,写注释是编程中最难的部分之一,我自己也常常在这方面挣扎。

3) 你用 print "";如果你只是想打印一个换行符,可以直接用 print(这会打印一个换行符),或者在你打印的字符串中加上"\n"(这是一个换行符,挺酷的),这样也能打印换行。试试看,你会明白我在说什么。

4) 与其测试布尔值像 if something == False,你可以简单地说 if not something,这样更清晰。同样地,如果你在测试 if something == True,你可以直接说 if something

5) 在我上面的解决方案中,我问自己“我想要得到什么”,而不是“我该如何从现在的位置到达目标”。这个区别很微妙,可能你会觉得“Isaac真傻”,我可能没有表达得很好,但我认为这是一个重要的区别!

祝你学习Python/编程顺利!

撰写回答