2

我最近在上一篇文章中问了一个关于高分问题的问题。这是一个类项目,所以应该比较简单。我还是这个网站的新手,所以我不确定如何干净地发布新的修订,所以如果您已经阅读了其中的一部分,我深表歉意。这次我只是要把整个程序放在这里。除高分部分外,一切正常。当我选择在玩游戏之前只检查高分列表时,输出效果很好,但是,在玩游戏后,返回主菜单然后再次检查高分我得到错误

列表索引必须是整数而不是 str

. 我认为这意味着我的原始分数列表设置不正确,但我并不完全确定。这是代码,我非常感谢您的帮助。这个网站非常适合这样。

import random
loop_game = True

while loop_game:
    questions= [
                {"question": "Who won the 2012 NFL Superbowl?",
                 "answers": ["Jacksonville Jaguars",
                            "Oakland Raiders",
                            "New York Giants",
                            "Baltimore Ravens"],
                 "correct": "4"},
                {"question": "Which song was at the top of the charts in early 2001, by OutKast?",
                 "answers": ["Bootylicious",
                             "Angel",
                             "Ms. Jackson",
                             "U Got It Bad"],
                "correct": "3"},
                {"question": "How many centimeters are one inch?",
                 "answers": ["2.12",
                             "2.54",
                             "3.24",
                             "3.38"],
                "correct": "2"}]

    scores=[{'initials': None,
             'score': -500}]

#main menu
    def main_menu():
        global loop_game
        print("""
***********************************************  
Welcome to The Greatest Trivia Show on Earth!!!
***********************************************
1. Play Game
2. High Scores
3. Credits
4. Instuctions
5. Quit
""")
        needs_input = True
        while needs_input:
          selection = input("Which Selection would you like? ")
          if selection == "1":
              play_game()
              needs_input = False
          elif selection == "2":
              display_scores()
              needs_input = False
          elif selection == "3":
              credits()
              needs_input = False
          elif selection == "4":
              instructions()
              needs_input == False
          elif selection == "5":
              needs_input = False
              loop_game = False
          else:
              print("\nSelect a valid option\n")

    def play_game():
        #definitions
        global total_points
        global questions
        loop_pa = True
        total_points = 3
        random.shuffle(questions)
        counter = 0
        #gets name in case of high score
        global hs_name
        hs_name = input("What are your initials?: ")


        #main play loop
        while counter < 2:
            for j in questions:
                counter += 1
                print("\n",j["question"])
                for i, choice in enumerate(j["answers"]):
                    print(str(i+1) + ". " + choice)
                answer = str(input("\nChoose an answer 1-4: "))
                if answer == j["correct"]:
                    print("\nGood job! You keep your precious points...this time!\n")
                else:
                    print("\nSorry, that is not correct. You lose one point.\n")
                    total_points -= 1
                    print("\nTotal Points: ",  total_points)

        #all questions have been read
        print("\nThat's it, your score is: ", total_points)

        #check/append best scores list
        best_scores()

        #keep playing loop
        while loop_pa:
            keep_playing = input("Play again?  (y, n) \n")
            if keep_playing == "y":
                print("\nAwesome! Here we go! \n\n")
                loop_pa = False
                play_game()
            elif keep_playing == "n":
                print("Ahh, too bad.  Thanks for playing!")
                loop_pa = False
                main_menu()
            else:
                print("Select a valid option\n")

    def best_scores():
        for i, score in enumerate(scores):
            if total_points > score['score']:
                scores[i:i+1] = {'initials': hs_name, 'score': total_points}
                del scores[5:]
                break

    def display_scores():
        print("HIGH\tSCORES")
        for score in scores:
            print(score['initials'], "\t", score['score'])

    def instructions():
        print("""

*************
Instructions
*************
The game is quite simple:  You start out with 12 points.
You lose a point for every incorrect answer.
If you get an answer correct, your score stays the same
and you move forward through the question set.  Try to
see how many points you can keep!
         """)
        main_menu()

    def credits():
        print("\nCreated by Jessica Gregg and Jason Vignochi\n")
        main_menu()


    main_menu()

编辑:哦!错误所在的行位于 display_scores 函数中(第 119 行)

print(score['initials'], "\t", score['score'])

4

3 回答 3

2

问题是这一行:

scores[i:i+1] = {'initials': hs_name, 'score': total_points}

当你替换一个序列的一个子片段时,你必须用另一个迭代来替换它。例如:

>>> a = [0, 1, 2, 3, 4]
>>> a[2:3] = [3] # fine
>>> a[2] = 3 # fine
>>> a[2:3] = 3
TypeError: can only assign an iterable

那么,为什么您的代码不是 a TypeError?因为 adict实际上一个可迭代的——它就像一个键列表。[{'initials': old_name, 'score': old_score}]因此,当您尝试用 dictionary替换子列表时{'initials': new_initials, 'score': new_score},它实际上看到的是['initials', 'score'].

因此,稍后,当您开始尝试打印分数时,其中一个不是 a dict,而是 string 'initials'。而您正试图将其用作 a dict,因此会出现错误。

如果您print(scores)在调用之前和之后,您可以更容易地看到这一点best_scores,并打印score出来display_scores

于 2013-10-15T20:41:35.983 回答
2

你搞砸scoresbest_scores()。第一次通过后的样子['score', 'initials']。切片分配需要一个可迭代对象,并且当用作可迭代对象时,确实 dict 会迭代其键。试试这个,看起来更简单(虽然我可能只是追加和排序):

def best_scores():
    global scores
    for i, score in enumerate(scores):
        if total_points > score['score']:
            scores.insert(i, {'initials': hs_name, 'score': total_points})
            scores = scores[:5]
            break

我的方式:

from operator import itemgetter

def best_scores():
    global scores
    scores.append({'initials': hs_name, 'score': total_points})
    scores = sorted(scores, key=itemgetter('score'), reverse=True)[:5]
于 2013-10-15T20:44:37.363 回答
-1

scores通过 using 定义为列表的列表[{}],因此可以按照您的需要引用它,使用scores[ 0 ][ 'initial' ]等。

于 2013-10-15T20:45:13.813 回答