Co to są „metody klasowe” i „metody instancji” w Pythonie?
„Metoda instancji” wykorzystuje informacje zawarte w instancji, aby dowiedzieć się, jaką wartość zwrócić (lub jaki efekt uboczny zrobić). Te są bardzo częste.
„Metoda klasy” wykorzystuje informacje o klasie (a nie instancji tej klasy), aby wpływać na to, co ona robi (są one zwykle używane do tworzenia nowych instancji jako alternatywnych konstruktorów, a zatem nie są niewiarygodnie powszechne).
„Metoda statyczna” nie wykorzystuje żadnych informacji o klasie lub instancji do obliczenia tego, co robi. Zwykle jest w klasie dla wygody. (Jako takie też nie są zbyt częste.)
Funkcja X
Pamiętasz klasę matematyczną: „y jest funkcją x f(x)
,?” Zastosujmy to w kodzie:
y = function(x)
Z powyższego wynika, że ponieważ x
może się zmienić, y
może ulec zmianie, gdy x
zmiany. To właśnie ma na myśli, gdy mówimy, że „ y
jest funkcją x
”
Co będzie y
kiedy z
będzie 1
? 2
? 'FooBarBaz'
?
y
nie jest funkcją z
, więc z
może być czymkolwiek i nie wpływać na wynik funkcji, zakładając, że nasza function
jest funkcją czystą. (Jeśli uzyskuje dostęp z
jako zmienna globalna, to nie jest to czysta funkcja - właśnie to oznacza funkcjonalna czystość.)
Pamiętaj o powyższym, czytając następujące opisy:
Metody instancji
Metoda wystąpienie jest funkcją jest funkcja o wystąpieniu . Funkcja przyjmuje instancję domyślnie jako argument, a instancja jest używana przez funkcję do określenia wyniku funkcji.
Wbudowanym przykładem metody instancji jest str. Niższy:
>>> 'ABC'.lower()
'abc'
str.lower
jest wywoływany w wystąpieniu ciągu i wykorzystuje informacje zawarte w wystąpieniu, aby dowiedzieć się, który nowy ciąg zwrócić.
Metody klasowe:
Pamiętaj, że w Pythonie wszystko jest przedmiotem. Oznacza to, że klasa jest obiektem i może być przekazana jako argument funkcji.
Metoda klasy jest funkcją, która jest funkcją z klasy . Akceptuje klasę jako argument.
Wbudowanym przykładem jest dict.fromkeys
:
>>> dict.fromkeys('ABC')
{'C': None, 'B': None, 'A': None}
Funkcja niejawnie zna swoją klasę, funkcja wykorzystuje klasę do wpływania na wynik funkcji i tworzy nową klasę z iterowalnego. OragedDict pokazuje to, używając tej samej metody:
>>> from collections import OrderedDict
>>> OrderedDict.fromkeys('ABC')
OrderedDict([('A', None), ('B', None), ('C', None)])
Metoda class wykorzystuje informacje o klasie (a nie instancji tej klasy), aby wpłynąć na typ klasy, który ma zostać zwrócony.
Metody statyczne
Wspominasz o metodzie, która „nie zna swojej klasy” - jest to metoda statyczna w Pythonie. Jest on jedynie dołączony dla wygody do obiektu klasy. Opcjonalnie może to być osobna funkcja w innym module, ale jej sygnatura wywołania byłaby taka sama.
Metoda statyczna nie jest funkcją klasy ani obiektu.
Wbudowanym przykładem metody statycznej jest str.maketrans z Python 3.
>>> str.maketrans('abc', 'bca')
{97: 98, 98: 99, 99: 97}
Biorąc pod uwagę kilka argumentów, tworzy słownik, który nie jest funkcją jego klasy.
Jest to wygodne, ponieważ str
jest zawsze dostępne w globalnej przestrzeni nazw, więc możesz łatwo używać go z funkcją translacji:
>>> 'abracadabra'.translate(str.maketrans('abc', 'bca'))
'bcrbabdbcrb'
W Pythonie 2 musisz uzyskać do niego dostęp z string
modułu:
>>> 'abracadabra'.translate(str.maketrans('abc', 'bca'))
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: type object 'str' has no attribute 'maketrans'
>>> import string
>>> 'abracadabra'.translate(string.maketrans('abc', 'bca'))
'bcrbabdbcrb'
Przykład
class AClass(object):
"""In Python, a class may have several types of methods:
instance methods, class methods, and static methods
"""
def an_instance_method(self, x, y, z=None):
"""this is a function of the instance of the object
self is the object's instance
"""
return self.a_class_method(x, y)
@classmethod
def a_class_method(cls, x, y, z=None):
"""this is a function of the class of the object
cls is the object's class
"""
return cls.a_static_method(x, y, z=z)
@staticmethod
def a_static_method(x, y, z=None):
"""this is neither a function of the instance or class to
which it is attached
"""
return x, y, z
Utwórzmy instancję:
>>> instance = AClass()
Teraz instancja może wywoływać wszystkie metody:
>>> instance.an_instance_method('x', 'y')
('x', 'y', None)
>>> instance.a_static_method('x', 'y')
('x', 'y', None)
>>> instance.a_class_method('x', 'y')
('x', 'y', None)
Ale klasa zwykle nie jest przeznaczona do wywoływania metody instancji, chociaż oczekuje się, że wywoła inne:
>>> AClass.a_class_method('x', 'y')
('x', 'y', None)
>>> AClass.a_static_method('x', 'y')
('x', 'y', None)
>>> AClass.an_instance_method('x', 'y')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: an_instance_method() missing 1 required positional argument: 'y'
Trzeba jawnie przekazać instancję, aby wywołać metodę instancji:
>>> AClass.an_instance_method(instance, 'x', 'y')
('x', 'y', None)