[Python-Dev] decorate-sort-undecorate
Geoffrey Talvola
gtalvola at nameconnector.com
Tue Oct 14 17:06:19 EDT 2003
Tim Peters wrote:
> [Geoffrey Talvola]
>> I disagree... I almost always use DSU in any circumstances because I
>> find it easier and more natural to write:
>>
>> def keyfunc(record):
>> return record.LastName.lower(), record.FirstName.lower(),
>> record.PhoneNumber mylist = sortUsingKeyFunc(mylist, keyfunc)
>
> You've left out the body of sortUsingKeyFunc, so I expect
> you're unusual in
> having built up helper routines for doing DSU frequently.
>
Yes, I do use a helper routine, but I suspect I'm not the only one out there
who does...
>> than to have to write an equivalent comparison function:
>>
>> def cmpfunc(r1, r2):
>> return cmp((r1.LastName.lower(), r1.FirstName.lower(),
>> r1.PhoneNumber), (r2.LastName.lower(),
>> r2.FirstName.lower(), r2.PhoneNumber))
>> mylist.sort(cmpfunc)
>
> This is wordier than need be, though, duplicating code for
> the purpose of
> making it look bad <wink>. I'd do
>
> mylist.sort(lambda a, b: cmp(keyfunc(a), keyfunc(b)))
I'm not a huge fan of lambdas from a readability perspective, so I'd
probably wrap _that_ up into a helper function if I didn't know about DSU.
The point I'm trying to make it that a key function is usually more natural
to use than a comparison function. You're right, DSU isn't the only way to
make use of a key function. But, I think it would be a good thing for
list.sort() to take a key function because it will guide users toward using
the cleaner key function idiom and therefore improve the readability of
Python code everywhere.
>
>> so for me, ease of use is the reason, not speed. Of course, it
>> doesn't _hurt_ that DSU is faster...
>
> If your records often tie on the result of keyfunc (doesn't
> look likely
> given the names you picked here), and your sortUsingKeyFunc() function
> doesn't inject the original list index (or otherwise force a cheap
> tie-breaker), DSU can be much slower than passing a custom comparison
> function. Not likely, though.
Not to worry, I do inject the original list index. For the record, here's
my helper function, probably not optimally efficient but good enough for me:
def sortUsingKeyFunc(l, keyfunc):
l = zip(map(keyfunc, l), range(len(l)), l)
l.sort()
return [x[2] for x in l]
- Geoff
More information about the Python-Dev
mailing list