Запуск этого:Как переопределить поведение в списке Python (итератор)?
class DontList(object):
def __getitem__(self, key):
print 'Getting item %s' % key
if key == 10: raise KeyError("You get the idea.")
return None
def __getattr__(self, name):
print 'Getting attr %s' % name
return None
list(DontList())
Производит это:
Getting attr __length_hint__
Getting item 0
Getting item 1
Getting item 2
Getting item 3
Getting item 4
Getting item 5
Getting item 6
Getting item 7
Getting item 8
Getting item 9
Getting item 10
Traceback (most recent call last):
File "list.py", line 11, in <module>
list(DontList())
File "list.py", line 4, in __getitem__
if key == 10: raise KeyError("You get the idea.")
KeyError: 'You get the idea.'
Как я могу изменить это так, что я буду получать []
, в то же время предоставляя доступ к этим ключам [1]
и т.д.?
(я попытался положить в def __length_hint__(self): return 0
, но это не помогает.)
Мой реальный случай использования: (для прочтения, если это будет полезно, не стесняйтесь игнорировать прошлое этой точки)
После применения a certain patch к неглазу, я нашел неприятный побочный эффект для моего патча. Имея __getattr__
, установите на мой класс Undefined
, который возвращает новый объект Undefined
. К сожалению, это означает, что list(iniconfig.invalid_section)
(где isinstance(iniconfig, iniparse.INIConfig)
) делает это (положить в простых print
с в __getattr__
и __getitem__
):
Getting attr __length_hint__
Getting item 0
Getting item 1
Getting item 2
Getting item 3
Getting item 4
И так далее до бесконечности.
Обратите внимание, что некоторые из этих ответов игнорировать некоторые аспекты списка (х) - это первый называют __iter__, а затем __len__ на том, что если существует, и затем будет проходить через итератор. Убедитесь, что, если __len__ имеет какие-либо побочные эффекты (на одном из моих объектов ему нужно пройти через сам итератор, чтобы узнать, сколько у него элементов), что он сбрасывается, когда это делается. – 2015-09-28 17:56:23