Reputation: 9528
I'm digging into Python 3.3 now and I wonder why some functions (for example, sorted()
, reversed()
) for managing collections/iterable are built-in but some are implemented as methods of collection objects? I can append item to list using method append()
, but to get a length of it I should using built-in function len()
. It seems inconsistent to me, but I think I just missing some point in new language.
Upvotes: 4
Views: 87
Reputation: 122486
The short answer is that these decisions were made for human reasons rather than technical reasons.
The reasoning for len()
versus obj.length()
is explained by Guido van Rossum (Python's Benevolent Dictator For Life):
First of all, I chose len(x) over x.len() for HCI reasons (def
__len__()
came much later). There are two intertwined reasons actually, both HCI:(a) For some operations, prefix notation just reads better than postfix — prefix (and infix!) operations have a long tradition in mathematics which likes notations where the visuals help the mathematician thinking about a problem. Compare the easy with which we rewrite a formula like x*(a+b) into x*a + x*b to the clumsiness of doing the same thing using a raw OO notation.
(b) When I read code that says len(x) I know that it is asking for the length of something. This tells me two things: the result is an integer, and the argument is some kind of container. To the contrary, when I read x.len(), I have to already know that x is some kind of container implementing an interface or inheriting from a class that has a standard len(). Witness the confusion we occasionally have when a class that is not implementing a mapping has a get() or keys() method, or something that isn’t a file has a write() method.
He also explains why sorted()
and reversed()
aren't methods:
Also note that many functions are defined in terms of informal interfaces; for example, reversed works on anything that supports random access to items and has a known length. In practice, implementing things like max, sum, map, any, in and others, as built-in functions and operators is actually less code than implementing them as methods for each and every type that needs to support them.
Upvotes: 5