Real-world use cases for map's None fill-in feature?

Raymond Hettinger python at rcn.com
Mon Jan 9 05:37:33 EST 2006


Duncan Booth wrote:
> One example of padding out iterators (although I didn't use map's fill-in
> to implement it) is turning a single column of items into a multi-column
> table with the items laid out across the rows first. The last row may have
> to be padded with some empty cells.

ANALYSIS
--------

This case relies on the side-effects of zip's implementation details --
the trick of windowing or data grouping with code like:  zip(it(),
it(), it()).  The remaining challenge is handling missing values when
the reshape operation produces a rectangular matrix with more elements
than provided by the iterable input.

The proposed function directly meets the challenge:

    it = iter(iterable)
    result = izip_longest(*[it]*group_size, pad='')

Alternately, the need can be met with existing tools by pre-padding the
iterator with enough extra values to fill any holes:

    it = chain(iterable, repeat('', group_size-1))
    result = izip_longest(*[it]*group_size)

Both approaches require a certain meaure of inventiveness, rely on
advacned tricks, and forgo readability to gain the raw speed and
conciseness afforded by a clever use of itertools.  They are also a
challenge to review, test, modify, read, or explain to others.

In contrast, a simple generator is trivially easy to create and read,
albiet less concise and not as speedy:

    it = iter(iterable)
    while 1:
        row = tuple(islice(it, group_size))
        if len(row) == group_size:
            yield row
        else:
            yield row + ('',) * (group_size - len(row))
            break

The generator version is plain, simple, boring, and uninspirational.
But it took only seconds to write and did not require a knowledge of
advanced itertool combinations.  It more easily explained than the
versions with zip tricks.


Raymond




More information about the Python-list mailing list