Should any() and all() take a key= argument?

  • Thread starter Steve R. Hastings
  • Start date
S

Steve R. Hastings

The list.sort() method accepts a "key=" parameter to let you specify a
function that will change the way it sorts. In Python 2.5, min() and
max() now accept a "key=" parameter that changes how the functions decide
min or max.

Should any() and all() take a key= argument?

Example:
lst = [2, 4, 42]
any(lst, key=lambda x: x == 42) True
all(lst, key=lambda x: x % 2 == 0)
True

The above could be done with generator expressions:
True


I kind of like the key= option. The need isn't as strong as with
..sort(), min(), and max(), but consistency can be a good thing. I'd
personally like to see key= anywhere it makes sense.
 
S

Steven D'Aprano

The list.sort() method accepts a "key=" parameter to let you specify a
function that will change the way it sorts. In Python 2.5, min() and
max() now accept a "key=" parameter that changes how the functions decide
min or max.

Should any() and all() take a key= argument?

Example:
lst = [2, 4, 42]
any(lst, key=lambda x: x == 42)
True

In my opinion, that's an abuse of the term "key".

Here's another way of doing it:

lst = [2, 4, 42]
any(map(lambda x: x==42, lst))

I kind of like the key= option. The need isn't as strong as with
.sort(), min(), and max(), but consistency can be a good thing. I'd
personally like to see key= anywhere it makes sense.

This isn't one of those places.
 
F

Felipe Almeida Lessa

Em Sáb, 2006-04-01 às 20:44 +1000, Steven D'Aprano escreveu:
Here's another way of doing it:

lst = [2, 4, 42]
any(map(lambda x: x==42, lst))

In fact, as we're talking about Python 2.5 anyway, it would be better
not to waste memory and use:

any(x == 42 for x in lst)
 
S

Steven D'Aprano

Em Sáb, 2006-04-01 às 20:44 +1000, Steven D'Aprano escreveu:
Here's another way of doing it:

lst = [2, 4, 42]
any(map(lambda x: x==42, lst))

In fact, as we're talking about Python 2.5 anyway, it would be better
not to waste memory and use:

any(x == 42 for x in lst)

You might be talking about Python 2.5, but I certainly am not. any()
and all() are easy to (almost) implement in earlier Python versions:

try:
any
except NameError:
# warning: this version will consume an iterator
def any(seq):
for s in seq:
if s: return True
return False

and similarly for all().

In any case, I question your assumption that the version using map must
automatically "waste memory". Iterators carry a certain amount of overhead
which lists do not. For small enough lists, that overhead will be smaller
than the extra memory used by the list. "Small enough" will depend on the
type of objects involved: big complex objects created on the fly by
the generator gives the generator the advantage, small simple objects
like ints give the list the advantage. As Python doesn't give us any way to
measure the memory used by an object, it is hard to say where that
cut-off lies, but my wild guess is that for ints, it would probably be in
the multiple tens.

But then, unless these are big complex objects, why are we
micro-optimizing our code anyway? I'm running a Python process, and
it is consuming 6.7MB of memory at the moment. Do I really care about
saving 80 or 100 bytes?, or even 100 kilobytes? I don't think so.
 
P

Paul Rubin

Steven D'Aprano said:
...
In any case, I question your assumption that the version using map must
automatically "waste memory".

There's also always itertools.imap.
But then, unless these are big complex objects, why are we
micro-optimizing our code anyway? I'm running a Python process, and
it is consuming 6.7MB of memory at the moment. Do I really care about
saving 80 or 100 bytes?, or even 100 kilobytes? I don't think so.

The idea is to write code to be assumption-free when possible. A
general purpose library function should work efficiently on big
complex objects even if some specific application might use it only
for small objects. Similarly, application programs that will stay in
use for a while should be written to be able to handle large workloads
even if the initial requirements are small, unless significant extra
development effort is needed.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,780
Messages
2,569,611
Members
45,281
Latest member
Pedroaciny

Latest Threads

Top