On 12/1/2018 2:08 PM, Steven D'Aprano wrote:

This proof of concept wrapper class could have been written any time
since Python 1.5 or earlier:


class lazymap:
     def __init__(self, function, sequence):

One could now add at the top of the file
   from collections.abc import Sequence

and here

    if not isinstance(sequence, Sequence):
        raise TypeError(f'{sequence} is not a sequence')

         self.function = function
         self.wrapped = sequence
     def __len__(self):
         return len(self.wrapped)
     def __getitem__(self, item):
         return self.function(self.wrapped[item])

For 3.x, I would add

        def __iter__: return map(self.function, self.sequence)

but your point that iteration is possible even without, with the old protocol, is well made.

It is fully iterable using the sequence protocol, even in Python 3:

py> x = lazymap(str.upper, 'aardvark')
py> list(x)
['A', 'A', 'R', 'D', 'V', 'A', 'R', 'K']


Mapped items are computed on demand, not up front. It doesn't make a
copy of the underlying sequence, it can be iterated over and over again,
it has a length and random access. And if you want an iterator, you can
just pass it to the iter() function.

There are probably bells and whistles that can be added (a nicer repr?
any other sequence methods? a cache?) and I haven't tested it fully.

For backwards compatibilty reasons, we can't just make map() work like
this, because that's a change in behaviour. There may be tricky corner
cases I haven't considered, but as a proof of concept I think it shows
that the basic premise is sound and worth pursuing.


--
Terry Jan Reedy

_______________________________________________
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/

Reply via email to