【问题标题】:if comparison from dictionary lists如果从字典列表中进行比较
【发布时间】:2015-03-01 08:15:16
【问题描述】:

我有一本字典

alice = {
    "name": "Alice",
    "homework": [100.0, 92.0, 98.0, 100.0],
    "quizzes": [82.0, 83.0, 91.0],
    "tests": [89.0, 97.0]
}

和一个取列表平均值的函数

def average(numbers):
    return float(sum(numbers))/len(numbers)

我想要 python 函数 get_average() 来读取字典。之后,我希望函数取字典中列表的平均值并将该列表的平均值乘以特定数字(家庭作业的评分权重为 0.10,测验为 .30,测试为 .60)并给出加权作业、测验和测试的总和。我正在使用 if 语句来检查从字典中的 for 循环中选择的列表是否是作业、测验或测试。

def get_average(alice):
    hw=0
    qz=0
    ts=0

    for assignment in student:
        if assignment== ["homework"]:  
            hw=average(assignment)*.10
        if assignment==["quizzes"]:
            qz=average(assignment)*.30
        if assignment==["tests"]:
            ts=average(assignment)*.60

    return hw+qz+ts

这只会返回零。应该是 91.15

【问题讨论】:

    标签: python if-statement for-loop dictionary


    【解决方案1】:

    其他答案绰绰有余。我只是想尝试一些不同的东西,从中获得一点乐趣。

    使用此方法,您可以轻松扩展标记标准的深度,而无需使用所有额外的if 语句将函数的大小扩展太多。它也更容易编辑,IMO,重复的次数更少,而且很重要。

    alice = {
        "name": "Alice",
        "homework": [100.0, 92.0, 98.0, 100.0],
        "quizzes": [82.0, 83.0, 91.0],
        "tests": [89.0, 97.0]
    }
    
    def average(numbers):
        return float(sum(numbers))/len(numbers)
    
    def get_average(student):
        criteria = {'homework': 0.10, 'quizzes': 0.30, 'tests': 0.60}
        return sum(y * average(student[x]) for (x,y) in criteria.iteritems())
    
    alice['average'] = get_average(alice)
    
    print alice
    

    希望这会有所帮助。

    【讨论】:

    • 对于 OP,虽然其他人只是在展示如何解决您的问题,但这个答案确实更像 Python,应该是您编写 Python 代码的方式。
    【解决方案2】:

    遍历字典会为您提供字典中的键。您需要使用平均函数的值。您还可以使用iteritems 同时循环遍历键和值:

    这应该可行:

    for assignment, scores in student.iteritems():
        if assignment=="homework":  
            hw=average(scores)*.10
        if assignment=="quizzes":
            qz=average(scores)*.30
        if assignment=="tests":
            ts=average(scores)*.60
    
    return hw+qz+ts
    

    您也可以只循环遍历字典,而不是使用 student[assignment] 来代替分数,但这需要每次循环迭代进行两次查找,因此最好使用 iteritems。

    【讨论】:

    • 我是 python 新手。当您输入“for assignment, scores....”时,分数是否也在字典中循环播放?
    • 在这种情况下,为了将来的兼容性,最好使用dict.items()而不是iteritems()
    • 如果他使用的是 python3 是的,但是对于 python2 的 iteritems 将减少内存和时间密集型......对于像这样的 3 元素字典来说,这并不重要,但原则上 iteritems应该显示。对吗?
    【解决方案3】:

    你的代码有几个错误:

    1. assignmentget_average() 函数中迭代学生的键,即'name''homework' 等。因此,将其与字符串 'homework' 进行比较,而不是与列表 ['homework'] 进行比较。
    2. 正如我所说,assignment 包含键,因此您需要使用该键的值调用average,即student[assignment]
    3. 您在get_average() 函数中迭代student 变量,所以它应该是get_average(student) 而不是get_average(alice)

    演示:

    >>> def get_average(student):  
    ...     hw=0
    ...     qz=0
    ...     ts=0
    ...     for assignment in student:
    ...     # assignment iterates over keys of student i.e., 'name', 'homework' etc. So compare it with string 'homework' not with list ['homework']
    ...         if assignment== "homework":  
    ...         # as I said assignment contains keys, so you need to call average with value of that key i.e., student[assignment]
    ...             hw=average(student[assignment])*.10
    ...         if assignment=="quizzes":
    ...             qz=average(student[assignment])*.30
    ...         if assignment=="tests":
    ...             ts=average(student[assignment])*.60
    ...     return hw+qz+ts
    ... 
    >>> def average(numbers):
    ...     return float(sum(numbers))/len(numbers)
    ... 
    >>> alice = {
    ...     "name": "Alice",
    ...     "homework": [100.0, 92.0, 98.0, 100.0],
    ...     "quizzes": [82.0, 83.0, 91.0],
    ...     "tests": [89.0, 97.0]
    ... }
    >>> get_average(alice)
    91.14999999999999
    

    【讨论】:

    • 感谢这也有效。我正确使用了字典格式
    【解决方案4】:

    如果您使用的是 python 3,请使用 items(),因为 iteritems() 已从该版本中删除:

    def get_average(alice):
    
        tot = 0
        for tests, grades in alice.items():   #iterates over keys and values
            if tests == "homework":
                tot += average(grades)*0.1
            if tests == "quizzes":
                tot += average(grades)*0.3
            if tests == "tests":
                tot += average(grades)*0.6
    
        return tot
    

    还有另一种使用字典理解的方法:

    def get_average(alice):
    
        tot = 0
        gen = {test: average(grades) for test, grades in alice.items() if isinstance(grades, list)}
        for test, grades in gen.items():
            if test == "homework":
                tot += grades*0.1
            if test == "quizzes":
                tot += grades*0.3
            if test == "tests":
                tot += grades*0.6
    
        return tot
    

    【讨论】:

      猜你喜欢
      • 2020-11-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-03-24
      • 2017-06-21
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多