Raymond Hettinger <[email protected]> added the comment:
FWIW, Joe Jevnik worked hard to squeeze every possible nanosecond out of these
calls because they were frequently used. Extending this API will tend to undo
his efforts.
The original intent of itemgetter() was to provide a minimal alternative to
writing a simple lambda -- it did not have the goal of being a parameterized
way to express all possible calling patterns -- it just aspired to be good at
the common cases. In particular, itemgetter/attrgetter/methodcaller aimed at
building key-functions for sorted/min/max/nlargest/nsmallest applied to a
homogenous list of records. In none of those cases would it have been common
or normal to have a missing fields with meaningful default values.
Over the years, we've had various requests to extend the functionality in all
kinds of exotic ways (i.e. multi-level gets like s[5][1][3] or Tcl-like
keyed-list chains). Some of those went far beyond the original scope, were
non-harmonious with the current API, or ended-up needing more complex and
complete solutions.
Most of the requests were rarely accompanied by meaningful use cases. For
example, the referenced python-ideas post only included toy examples and its
sole expressed motivation was a half thought-out notion of consistency with
getattr(). The consistency argument doesn't make much sense because the
itemgetter() and attrgetter() API had already gone down a different road. The
getattr() function only looks-up one attribute, while the itemgetter() and
attrgetter() callable factories do multiple lookups such as
attrgetter(lastname, firstname) or itemgetter(3, 8, 2). It isn't clear that a
default argument would make sense for those cases, nor would it handle cases
where only one field had a default value but the others did not (I expect this
would likely be more common than having a meaningful default value for every
field). Also, since multiple positional arguments are allowed, the default
parameter would have to be a keyword argument (which isn't parallel with
getattr()).
IIRC, GvR at one time rejected a request for a list.get(index, default) method
on the basis that it rarely made sense for indexed lookups; however, that seems
very much like what is being proposed here for itemgetter().
Lastly, I'm concerned that every bit of extra functionality makes this API more
complex (meaning harder to learn and remember) and makes it slower (undoing
previous optimization efforts in order to speed-up its primary use cases for
namedtuple() and as a key function).
Even now, these APIs have are complex enough to where very fewer developers
even know what functionality is already provided. Even Python experts won't
immediately have correct interpretations for the likes of methodcaller('name',
'foo', bar=1) or itemgetter(slice(2,None))('ABCDEFG'). In both cases (both of
which are documented), the code would be better-off with a plain lambda or def.
ISTM that pushing the itemgetter/attrgetter/methodcaller API further would be
a readability anti-pattern.
If this does go forward, I think we should look for some actual use cases in
real code to help inform the decision of whether this would be an net win or
whether it would result in code that wouldn't pass a code review.
----------
assignee: rhettinger ->
_______________________________________
Python tracker <[email protected]>
<https://bugs.python.org/issue14384>
_______________________________________
_______________________________________________
Python-bugs-list mailing list
Unsubscribe:
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com