用户得分保存计划

时间:2015-02-04 16:40:47

标签: python

我正在尝试创建一个程序,它会询问用户的姓名,然后是一系列问题。每次问题正确时添加一个点。我试图将分数与用户名称一起存储到文本文件中,因此它在文本文件中看起来如此:

Name    Score 

所以让我们以约翰为例,如果他得到4分,那么它会写在文本文件中:

John    4

但我想要它,以便John再次参加考试,而不是让John两次:

John    4
John    6

我想要阅读:

John    4   6

不是重写名称和分数,而是将标签写入标签,然后将分数写入与名称为John in的同一行。

到目前为止,这是我的代码:

import random
name = input("Hello user, what is your name?")
count = (0)
score = (0)
while count != (8):
    count = count + (1)
    symbols = ['+', '-', '*']
    valueF = random.randint(1,10)
    valueS = random.randint(1,10)
    chosensymb = random.choice (symbols)
    question = input("What is %d %s %d ? :"%(valueF, chosensymb, valueS))
    answer = eval(str(valueF) + chosensymb + str(valueS))
    if question == str(answer):            
        score = score + (1)
        print ("Correct")
    else:
        print ("Incorrect")

print("%s, you have scored %d points"%(name,score))
filewrite = open("ScoreSheet.txt","a")
filewrite.write("\n%s\t%d"%(name,score))
filewrite.close()

我不知道怎么做,我是python的新手,如果我犯了任何错误,对不起,谢谢!

3 个答案:

答案 0 :(得分:2)

使用serializepickle只需json您的数据。以下是使用json序列化分数的示例(将分数存储在dict中 - 名称和分数之间的映射):

# import the serializing library
import json as serializer

现在,我们将创建一个功能,将分数写入给定文件:

def write_score(score_file_name, name, score):
    scores = read_scores(score_file_name)
    # add score
    scores[name] = score
    with open(score_file_name, 'w') as f:
        serializer.dump(scores, f)

它的作用是:

  1. 从分数文件(dict
  2. 加载序列化结果对象
  3. 更新分数dict(添加密钥/密钥更新值)
  4. 将更新的dict写入文件(使用json.dump
  5. 在编写write_score函数时,我们错过了read_scores函数,这使我们能够查看当前分数。所以,让我们写下这个read_scores

    def read_scores(score_file_name):
        try:
            with open(score_file_name, 'r') as f:
                scores = serializer.load(f)
            return scores
        except IOError:
            # if file does not exist - we have no scores
            return {}
    

    read_scores的作用是:

    1. 阅读序列化的dict(使用json.load
    2. 现在我们可以测试它是否真的有效。这是一个小例子:

      # set the score file name
      SCORES_FILE_NAME = 'scores.txt'
      
      write_score(SCORES_FILE_NAME, 'john', 10)    
      print(read_scores(SCORES_FILE_NAME))
      
      write_score(SCORES_FILE_NAME, 'jim', 11)    
      print(read_scores(SCORES_FILE_NAME))
      
      # overwrite john's score
      write_score(SCORES_FILE_NAME, 'john', 12)
      print(read_scores(SCORES_FILE_NAME))
      

      提示1 :您可能希望在撰写分数时使用name.lower(),以便johnJohn被视为同一用户。

      提示2:因为我们将json库引用为serializer,并且它与pickle具有相同的API,您可以在两者之间进行选择将import json as serializer替换为import pickle as serializer只需确保删除分数文件,因为它们不会以相同的方式序列化数据

      整个代码在一起:

      # import the serializing library
      import json as serializer
      
      def write_score(score_file_name, name, score):
          scores = read_scores(score_file_name)
          # add score
          scores[name] = score
          with open(score_file_name, 'w') as f:
              serializer.dump(scores, f)
      
      
      def read_scores(score_file_name):
          try:
              with open(score_file_name, 'r') as f:
                  scores = serializer.load(f)
              return scores
          except IOError:
              # if file does not exist - we have no scores
              return {}
      
      # TESTS
      
      # set the score file name
      SCORES_FILE_NAME = 'scores.txt'
      
      write_score(SCORES_FILE_NAME, 'john', 10)
      print(read_scores(SCORES_FILE_NAME))
      
      write_score(SCORES_FILE_NAME, 'jim', 11)
      print(read_scores(SCORES_FILE_NAME))
      
      # overwrite john's score
      write_score(SCORES_FILE_NAME, 'john', 12)
      print(read_scores(SCORES_FILE_NAME))
      

      输出:

      {u'john': 10}
      {u'john': 10, u'jim': 11}
      {u'jim': 11, u'john': 12}
      

      要阅读特定分数,您可以使用现有方法read_scores

      def read_score(score_file_name, name):
          return read_scores(score_file_name)[name]
      

      奖金 - Closures

      如果您了解闭包,则可以使用以下方式创建特定于文件的函数:

      def write_score(score_file_name):
          # create closure specific to 'score_file_name'
          def write_score_specific(name, score):
              scores = read_scores(score_file_name)
              # we're going to make a 'read_scores' with closures as well!
              # so use that one...
              scores_reader = read_scores(score_file_name)
              scores = scores_reader()
      
      
              # add score
              scores[name] = score
              with open(score_file_name, 'w') as f:
                  serializer.dump(scores, f)
      
          # return file-specific function
          return write_score_specific
      

      现在,我们只需要使用文件名参数一次来调用该函数,从那一刻起我们就可以使用结果ot写分数:

      # create specific 'write_score' for our file
      score_txt_writer = write_score('scores.txt')
      
      # update john's score to 10 without specifying the file
      score_txt_writer('john', 10)
      

      read_score相同:

      def read_scores(score_file_name):
          # create closure function
          def read_scores_specific():
              try:
                  with open(score_file_name, 'r') as f:
                      scores = serializer.load(f)
                  return scores
              except IOError:
                  # if file does not exist - we have no scores
                  return {}
          return read_scores_specific
      

      包含闭包的整个代码:

      # import the library
      import serializer
      
      # CLOSURES
      
      SCORES_FILE = 'scores.txt'
      def read_scores(score_file_name):
          # create closure function
          def read_scores_specific():
              try:
                  with open(score_file_name, 'r') as f:
                      scores = serializer.load(f)
                  return scores
              except IOError:
                  # if file does not exist - we have no scores
                  return {}
          return read_scores_specific
      
      def write_score(score_file_name):
          # create closure specific to 'score_file_name'
          def write_score_specific(name, score):
              scores_reader = read_scores(score_file_name)
              scores = scores_reader()
              # add score
              scores[name] = score
              with open(score_file_name, 'w') as f:
                  serializer.dump(scores, f)
      
          # return file-specific function
          return write_score_specific
      
      # create specific 'write_score' for our file
      score_txt_writer = write_score(SCORES_FILE)
      
      # update john's score to 10 without specifying the file
      score_txt_writer('john', 10)
      
      
      score_txt_reader = read_scores(SCORES_FILE)
      
      print score_txt_reader()
      

      输出:

      {u'john': 10}
      

答案 1 :(得分:1)

这不是文件访问的工作原理:在文件中,你不能只是在某处“插入”新值,向后移动文件的其余部分;你只能覆盖字符或重写整个文件。

通常,只要您的文件很短,如果重写整个文件,您将不会注意到任何性能影响。

答案 2 :(得分:1)

嗯,首先,你可以将每个人的分数存储在字典中。 让我们介绍一个scores对象:

scores = {}

它将名称作为键,分数作为值。像那样:

scores = {'John': 2,
          'Mary': 5}

如果你介绍一个新玩家,我们将在所述词典中创建一个新元素,让我们称之为'John',得分为0

scores['John'] = 0

然后,如果玩家猜对了,我们会增加玩家的分数:

scores['John'] += 1

(如果您只是想在对象中添加内容,可以使用+=运算符。这是一种较短的说法scores['John'] = scores['John'] + 1

然后魔法开始了!
Python中有一个名为pickle的内置模块,它可以将对象(比如我们已经制作的字典 - scores)存储在文件中,然后将它们从文件中弹出,它们和#39;重新恢复!

a quick manual如何使用pickleimport pickle pickle.dump(scores, open("scores.p", "wb")) 。简而言之,您将分数保存到文件中:

scores = pickle.load(open("scores.p", "rb"))

然后加载它:

{{1}}

这不是真正存储内容的最佳方式 - 还有更多内容,例如jsoncsvsqlite甚至是手动读/写,但是你&#39 ;现在可以了:)