The "best" way to way to delegate __iter__ would be:
def __iter__(self):
return iter(self._iterable)
Alternately, it might be worth knowing about:
def __iter__(self):
for item in self._iterable:
yield item
Which will let you fiddle with each item before returning it (ex, if you wanted yield item * 2).
And as @Lattyware mentions in the comments, PEP380 (slated for inclusion in Python 3.3) will allow:
def __iter__(self):
yield from self._iterable
Note that it may be tempting to do something like:
def __init__(self, iterable):
self.__iter__ = iterable.__iter__
But this won't work: iter(foo) calls the __iter__ method on type(foo) directly, bypassing foo.__iter__. Consider, for example:
class SurprisingIter(object):
def __init__(self):
self.__iter__ = lambda self: iter("abc")
def __iter__(self):
return iter([1, 2, 3])
You would expect that list(SurprisingIter()) would return ["a", "b", "c"], but it actually returns [1, 2, 3].
yield from self._iterable(this is accepted for inclusion in 3.3).