Python - 使用键从列表中访问类
有没有办法让一个类的列表在Python中像集合一样工作?
简单来说,我正在开发一个软件,它需要进行复杂的字符串比较。我为处理这些字符串创建了一个自定义类。因此,每个字符串都有一个类的实例。
结果就是,我有一个很大的列表,里面包含了所有这些类。我希望能够像这样访问它们:list[key]
,这里的key是基于字符串的(注意:一旦类被创建,这个字符串就不会改变,所以它应该是可以哈希的)。
我觉得我应该能比较简单地做到这一点,比如在类中添加一些像__cmp__
这样的东西,但要么是我理解得不够清楚(很可能),要么是我在文档中遗漏了什么。
基本上,我想能够做到类似这样的事情(Python提示符示例):
>>class a:
... def __init__(self, x):
... self.var = x
...
>>> from test import a
>>> cl = set([a("Hello"), a("World"), a("Pie")])
>>> print cl
set([<test.a instance at 0x00C866C0>, <test.a instance at 0x00C866E8>, <test.a instance at 0x00C86710>])
>>> cl["World"]
<test.a instance at 0x00C866E8>
谢谢!
编辑 一些额外的调整:
class a:
... def __init__(self, x):
... self.var = x
... def __hash__(self):
... return hash(self.var)
...
>>> v = a("Hello")
>>> x = {}
>>> x[v]=v
>>> x["Hello"]
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
KeyError: 'Hello'
>>> x["Hello"]
5 个回答
1
集合(set)和字典(dict)会使用一个对象的 __hash__
方法返回的值来查找这个对象,所以这样做就能达到你想要的效果:
>>class a:
... def __init__(self, x):
... self.var = x
...
... def __hash__(self):
... return hash(self.var)
2
你为什么不直接这样做呢:
>>> v = MyStr("Hello")
>>> x = {}
>>> x[v.val]=v
>>> x["Hello"]
MyStr("Hello")
为什么要费那么大劲去创建一个自定义的字典,使用的键还和你传入的不同呢?(比如用“Hello”而不是 MyStr("Hello"))。
举个例子:
class MyStr(object):
def __init__(self, val):
self.val = str(val)
def __hash__(self):
return hash(self.val)
def __str__(self):
return self.val
def __repr__(self):
return 'MyStr("%s")' % self.val
>>> v = MyStr("Hello")
>>> x = {}
>>> x[str(v)]=v
>>> x["Hello"]
MyStr("Hello")
2
只需要写一个类,让它的行为有点像一个映射(就像字典那样):
class ClassDict(object):
def __init__(self):
self.classes = {}
def add(self, cls):
self.classes[cls.__name__] = cls
def remove(self, cls):
if self.classes[cls.__name__] == cls:
del self.classes[cls.__name__]
else:
raise KeyError('%r' % cls)
def __getitem__(self, key):
return self.classes[key]
def __repr__(self):
return 'ClassDict(%s)' % (', '.join(self.classes),)
class C(object):
pass
class D(object):
pass
cd = ClassDict()
cd.add(C)
cd.add(D)
print cd
print cd['C']