首页 文章

使用相同键的(嵌套)词典的Pythonic替代?

提问于
浏览
6

我发现自己避免使用词典,因为通常,将近一半的代码是重复的 . 我通常在嵌套字典中执行此操作,其中所有子字典包含相同的键,但具有不同的值 .

我手动创建一个大的父字典,其中每个键包含一个嵌套字典,用于外部模块 . 嵌套字典都使用相同的键来定义配置参数 . 这种用法是明确的并且有效但是为我手动创建的每个嵌套字典重新键入或复制/粘贴密钥感觉很愚蠢 . 我并不过分担心优化内存或性能,只是想知道我是否应该采用另一种更多的Pythonic方式 .

作为一个简单的例子和模式经常看到:

people_dict = {
    "Charles Lindberg": {"address": "123 St.", 
                         "famous": True}, 
    "Me": {"address": "456 St.",
           "famous": False}
    }

>>>people_dict["Charles Lindberg"]["address"]
"123 St."

虽然字典启用了显式代码,但是使用重复键定义嵌套字典会很繁琐且容易出错 . 在此示例中,嵌套字典的一半是所有嵌套字典共有的代码重复代码 . 我已经尝试使用元组来消除重复的密钥,但发现这导致了脆弱的代码 - 位置的任何变化(而不是字典密钥)都会失败 . 这也导致代码不明确且难以遵循 .

people_dict = {
        "Charles Lindberg": ("123 St.", True), 
        "Me": ("456 St.", False),
        }    

>>>people_dict["Charles Lindberg"][0]
"123 St."

相反,我编写了一个类来封装相同的信息:这成功地减少了重复代码......

class Person(object):
    def __init__(self, address, famous=False):
        self.address = address
        self.famous = famous

people_dict = [
    "Charles Lindberg": Person("123 St.", famous=False), 
    "Me": Person("456 St."), 
    ]

>>>people_dict["Charles Lindberg"].address
"123 St."

创建一个类似乎有点矫枉过正......标准数据类型似乎太基础了......

我想有更好的方法在Python中完成这个,而不必编写自己的类?

使用公共密钥创建嵌套字典时,避免重复代码的最佳方法是什么?

3 回答

  • 0

    听起来你有一个数据矩阵,因为每个“行”都有相同的键(列),所以我使用NumPy数组:

    import numpy as np
    
    dtype = [('name', object), ('address', object), ('famous', bool)]
    people = np.array([
            ("Charles Lindberg", "123 St.", True),
            ("Me", "456 St.", False),
            ], dtype)
    
    charlie = people[people['name'] == 'Charles Lindberg'][0]
    print charlie['address']
    

    或者使用更高级别的Pandas:

    import pandas as pd
    people = pd.DataFrame(people_dict)
    print people['Charles Lindberg']['address']
    

    这样可以非常轻松地将原始字典直接加载到矩阵中,并为您提供类似的查找功能 .

  • 0

    如果你想要一个dict,其中所有的值都是相同或相似的键,你可以定义一个取值的函数并返回一个内部的dicts .

    def hash(address, famous): return {"address": address, "famous": famous}
    
    people_dict = {
        "Charles Lindberg": hash("123 St.", true),
        "Me": hash("456 St.", false)
    }
    
  • 3

    首先,您可以阅读上面的链接以获取有关nametuples的更多信息:https://docs.python.org/2/library/collections.html#collections.namedtuple

    NamedTuples可以帮助您避免"duplicate code" . 您可以为地址创建一个namedtuple并使用它来定义 .
    我特别喜欢Object . OO有更好的解决方案来解决这个问题 . 您可以创建一个方法来将对象导出到dict .

    对于功能范例来说,更好的是使用list,array和dict,因为有很多方法/函数来帮助这个结构(map,reduce等) . 如果您没有假装在应用程序中使用某些功能,请转到OO(面向对象)解决方案 .

    关心安德烈

相关问题