繁体   English   中英

除了字符串和整数之外的Python字典键?

[英]Python dictionary keys besides strings and integers?

任何人都有一些简洁的字典示例,其中包含一些有趣的键(除了规范字符串或整数),以及您在程序中如何使用它们?

我理解我们所需要的一个键是可以hashable ,这意味着它必须是不可变的和可比较的(具有__eq__()__cmp__()方法)。

一个相关的问题是:我怎样才能快速,顺畅地定义新的可hashable

让我们去寻找一些更深奥的东西。 假设您想要执行一系列函数并存储每个函数的结果。 对于引发异常的每个函数,您希望记录异常,并且还要计算引发每种异常的次数。 函数和异常可用作dict键,因此这很容易:

funclist = [foo, bar, baz, quux]

results    = {}
badfuncs   = {}
errorcount = {}

for f in funclist:
    try:
        results[f] = f()
    except Exception as e:
        badfuncs[f]   = e
        errorcount[type(e)] = errorcount[type(e)] + 1 if type(e) in errorcount else 1

现在你可以if foo in badfuncs执行if foo in badfuncs来测试该函数是否引发异常(或者if foo in results中查看它是否正常运行), if ValueError in errorcount以查看是否有任何函数引发了ValueError ,依此类推。

您可以使用元组作为键,例如,如果要创建多列索引。 这是一个简单的例子:

>>> index = {("John", "Smith", "1972/01/01"): 123, ("Bob", "Smith", "1972/01/02"): 124}
>>> index
{('Bob', 'Smith', '1972/01/02'): 124, ('John', 'Smith', '1972/01/01'): 123}
>>> index.keys()
[('Bob', 'Smith', '1972/01/02'), ('John', 'Smith', '1972/01/01')]
>>> index['John', 'Smith', '1972/01/01']
123

有关如何使用dict作为键(可以使用dict)的示例,请参阅以下答案: Python hashable dicts

你忽略了一个对象是可能是最重要的方法可哈希__hash__()

您自己的哈希类型的最短实现是这样的:

class A(object):
    pass

现在您可以使用A实例作为字典键:

d = {}
a = A()
b = A()
d[a] = 7
d[b] = 8

这是因为默认情况下用户定义的类是可清除的,并且它们的哈希值是它们的id - 所以如果它们是同一个对象,它们只会相等。

请注意, A实例绝不是不可变的,但它们仍然可以用作字典键。 字典键必须是不可变的语句仅适用于内置类型。

请注意,我从来没有真正使用过这个,但我一直以为使用元组作为键可以让你做一些有趣的事情。 例如,我会发现它是一种映射网格坐标的便捷方式。 您可以将其视为视频游戏中的网格(可能是某种类似Fire Emblem的战术游戏):

>>> Terrain = { (1,3):"Forest", (1,5):"Water", (3,4):"Land" }
>>> print Terrain
{(1, 5): 'Water', (1, 3): 'Forest', (3, 4): 'Land'}
>>> print Terrain[(1,3)]
Forest
>>> print Terrain[(1,5)]
Water
>>> x = 3
>>> y = 4
>>> print Terrain[(x,y)]
Land

这样的事情。

编辑:正如Mark Rushakof在评论中指出的那样,我基本上打算将其作为一个稀疏数组

我不知道你为什么要这样做(最好要这样做)......但除了字符串和整数之外,你也可以同时使用它们。 也就是说,作为初学者,我发现它既强大又令人惊讶:

foo = { 1:'this', 2:'that', 'more':'other', 'less':'etc' }

是一个完全有效的字典,它提供对foo[2]访问,就像它对foo['more']一样容易。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM