Während der Grund größtenteils historisch ist, gibt es in Pythons einige Besonderheiten len, die die Verwendung einer Funktion anstelle einer geeigneten Methode erforderlich machen.
Einige Operationen in Python sind als Methoden implementiert, zum Beispiel list.indexund dict.append, während andere als Callables und magische Methoden implementiert werden, zum Beispiel strund iterund reversed. Die beiden Gruppen unterscheiden sich so stark, dass der unterschiedliche Ansatz gerechtfertigt ist:
- Sie sind häufig.
str, intUnd Freunde sind Typen. Es ist sinnvoller, den Konstruktor aufzurufen.
- Die Implementierung unterscheidet sich vom Funktionsaufruf. Kann beispielsweise
iteraufrufen, __getitem__wenn __iter__es nicht verfügbar ist, und unterstützt zusätzliche Argumente, die nicht in einen Methodenaufruf passen. Aus dem gleichen Grund it.next()wurde next(it)in neueren Versionen von Python geändert - es ist sinnvoller.
- Einige davon sind nahe Verwandte von Betreibern. Es gibt eine Syntax für den Aufruf
__iter__und __next__- es heißt die forSchleife. Aus Gründen der Konsistenz ist eine Funktion besser. Und es macht es für bestimmte Optimierungen besser.
- Einige der Funktionen sind den anderen einfach viel zu ähnlich - verhält sich
reprwie strsie. Mit im str(x)Vergleich x.repr()wäre verwirrend.
- Einige von ihnen verwenden beispielsweise selten die eigentliche Implementierungsmethode
isinstance.
- Einige von ihnen sind tatsächliche Betreiber,
getattr(x, 'a')sind eine andere Art x.aund Weise und getattrteilen viele der oben genannten Eigenschaften.
Ich persönlich nenne die erste Gruppe methodenähnlich und die zweite Gruppe operatorähnlich. Es ist keine sehr gute Unterscheidung, aber ich hoffe, es hilft irgendwie.
Trotzdem lenpasst es nicht genau in die zweite Gruppe. Es ist näher an den Operationen im ersten, mit dem einzigen Unterschied, dass es weitaus häufiger ist als fast alle anderen. Aber das einzige, was es tut, ist anzurufen __len__, und es ist sehr nahe L.index. Es gibt jedoch einige Unterschiede. Zum Beispiel __len__könnte für die Implementierung anderer Funktionen aufgerufen werden, z. B. boolwenn die Methode aufgerufen wurde len, könnten Sie bool(x)mit einer benutzerdefinierten lenMethode brechen , die völlig andere Dinge tut.
Kurz gesagt, Sie haben eine Reihe sehr häufiger Funktionen, die Klassen implementieren können, auf die über einen Operator, über eine spezielle Funktion (die normalerweise mehr als die Implementierung als Operator ausführt), während der Objektkonstruktion und auf alle zugegriffen werden kann einige gemeinsame Merkmale teilen. Der Rest ist eine Methode. Und lenist eine Ausnahme von dieser Regel.
len()oderreversed()gilt für viele Arten von Objekten, aber eine Methode wieappend()nur für Sequenzen usw.