如何使用 .get() 方法获取嵌套字典的键值对

28

使用一个简单的字典,例如:

myDict = {'key1':1, 'key2':2}

我可以安全地使用:

print myDict.get('key3')

即使'key3'不存在,.get()仍然返回None,因此不会抛出任何错误。

现在我如何使用嵌套键字典实现相同的简单性:

myDict={}
myDict['key1'] = {'attr1':1,'attr2':2}
以下会引发KeyError错误:
print myDict.get('key1')['attr3']

这将会通过:

print myDict.get('key1').get('attr3')

但它将失败,出现AttributeError: 'NoneType' object has no attribute 'get'的错误:

print myDict.get('key3').get('attr1')

参见:https://dev59.com/dXE95IYBdhLWcg3wV8e_ - dreftymac
6个回答

50

dict.get 接受额外的 default 参数。如果没有这样的键,则返回 default 参数指定的值,而不是 None

print myDict.get('key1', {}).get('attr3')

谢谢!很好知道! - alphanumeric
参见:https://dev59.com/dXE95IYBdhLWcg3wV8e_ - dreftymac
2
请注意,如果明确设置了myDict['key1'] = None,那么myDict.get('key1', {})仍然可能返回None。我实际上建议使用这种方法 - Pavel Vergeev
@PavelVergeev,我的回答和你链接的另一个回答在这种情况下都会引发“TypeError:'NoneType'对象没有属性'getitem'”;) - falsetru
空花括号中可以传递什么?这是用来做什么的?谢谢。 - Gel
1
@Gel,Python中的{}是一个字典(哈希映射)字面量。如果myDict中没有'key1'条目,则它被用作回退值。 - falsetru

8

有一篇非常好的关于嵌套字典的Dan O'Huiginn的博客文章。他最终建议使用一个处理嵌套更好的类来子类化dict。这里是修改后的子类,用于处理试图访问非dict值的键的情况:

class ndict(dict):
     def __getitem__(self, key):
         if key in self: return self.get(key)
         return self.setdefault(key, ndict())

您可以引用嵌套的现有键或不存在的键。 您可以安全地使用括号表示法进行访问,而不是使用 .get() 方法。 如果 NestedDict 对象上不存在键,则会返回一个空的 NestedDict 对象。 初始化可能有点冗长,但如果需要该功能,则可能适用于您。 以下是一些示例:

In [97]: x = ndict({'key1': ndict({'attr1':1, 'attr2':2})})

In [98]: x
Out[98]: {'key1': {'attr1': 1, 'attr2': 2}}

In [99]: x['key1']
Out[99]: {'attr1': 1, 'attr2': 2}

In [100]: x['key1']['key2']
Out[100]: {}

In [101]: x['key2']['key2']
Out[101]: {}

In [102]: x['key1']['attr1']
Out[102]: 1

6

使用异常:

try:
    print myDict['key1']['attr3']
except KeyError:
    print "Can't find my keys"

1
现在为什么我就不能想到那个呢?! - Captain Lepton

0

NestedDict 允许您使用标准字典的相同接口处理嵌套字典。

from ndicts.ndicts import NestedDict

my_dict = {'key1': {'attr1': 1,'attr2': 2}
nd = NestedDict(my_dict)

>>> nd.get(("key1", "attr3"), "not found")
'not found'
>>> nd.get(("key3", "attr1"), "not found")
'not found'

安装ndicts

pip install ndicts

0

这很正常,因为key3不存在

myDict.get('key3')

返回空值..

NoneType对象没有属性..

因此,您必须存储myDict.get('key3')的值,测试它是否不为空,然后在存储的项目上使用get方法。


0

我改进了 jxstandford 提出的处理字典中列表的方案。

class NestedDict(dict):

    def __getitem__(self, key):
        if key in self:
            return self.to_nested(self.get(key))
        return self.setdefault(key, NestedDict())


    @staticmethod
    def to_nested(obj: Any) -> Any:
        if not obj:
            return NestedDict()
        if isinstance(obj, dict):
            return NestedDict(obj)
        if isinstance(obj, list):
            return list(map(NestedDict.to_nested, obj))
        return obj

所以它可以处理像这样的字典:

foo = {"bar": [{"a:":3}]}
{} == foo["bar"][0]["b"]

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接