Odpowiedzi:
Tak, po prostu użyj nazwy metody, tak jak napisałeś. Metody / funkcje są obiektami w Pythonie, tak jak wszystko inne, i możesz przekazywać je w sposób, w jaki robisz zmienne. W rzeczywistości można myśleć o metodzie (lub funkcji) jako zmiennej, której wartością jest rzeczywisty obiekt kodu, który można wywołać.
Do Twojej wiadomości, nie ma call
metody - myślę, że się nazywa __call__
, ale nie musisz jej jawnie wywoływać:
def method1():
return 'hello world'
def method2(methodToRun):
result = methodToRun()
return result
method2(method1)
Jeśli chcesz method1
zostać wywołany argumentami, sprawy stają się nieco bardziej skomplikowane. method2
musi być napisany z odrobiną informacji o tym, jak przekazywać argumenty method1
, i musi skądś uzyskać wartości dla tych argumentów. Na przykład, jeśli method1
ma przyjąć jeden argument:
def method1(spam):
return 'hello ' + str(spam)
wtedy możesz napisać, method2
aby to wywołać z jednym argumentem, który zostanie przekazany:
def method2(methodToRun, spam_value):
return methodToRun(spam_value)
lub z argumentem, że oblicza się:
def method2(methodToRun):
spam_value = compute_some_value()
return methodToRun(spam_value)
Możesz rozwinąć to do innych kombinacji przekazywanych wartości i obliczanych wartości, takich jak
def method1(spam, ham):
return 'hello ' + str(spam) + ' and ' + str(ham)
def method2(methodToRun, ham_value):
spam_value = compute_some_value()
return methodToRun(spam_value, ham_value)
lub nawet z argumentami słów kluczowych
def method2(methodToRun, ham_value):
spam_value = compute_some_value()
return methodToRun(spam_value, ham=ham_value)
Jeśli nie wiesz, podczas pisania method2
, jakie argumenty methodToRun
chcesz wziąć, możesz również użyć rozpakowywania argumentów, aby wywołać je w ogólny sposób:
def method1(spam, ham):
return 'hello ' + str(spam) + ' and ' + str(ham)
def method2(methodToRun, positional_arguments, keyword_arguments):
return methodToRun(*positional_arguments, **keyword_arguments)
method2(method1, ['spam'], {'ham': 'ham'})
W takim przypadku positional_arguments
musi to być lista, krotka lub podobne i keyword_arguments
jest to dykt lub podobne. W method2
możesz zmodyfikować positional_arguments
i keyword_arguments
(np. Dodać lub usunąć niektóre argumenty lub zmienić wartości) przed wywołaniem method1
.
Tak to mozliwe. Po prostu nazwij to:
class Foo(object):
def method1(self):
pass
def method2(self, method):
return method()
foo = Foo()
foo.method2(foo.method1)
def method1(): pass def method2(method) return method() method2(method1)
Oto Twój przykład przepisany od nowa, aby pokazać samodzielny przykład działania:
class Test:
def method1(self):
return 'hello world'
def method2(self, methodToRun):
result = methodToRun()
return result
def method3(self):
return self.method2(self.method1)
test = Test()
print test.method3()
Tak; funkcje (i metody) są obiektami pierwszej klasy w Pythonie. Następujące prace:
def foo(f):
print "Running parameter f()."
f()
def bar():
print "In bar()."
foo(bar)
Wyjścia:
Running parameter f().
In bar().
Na tego rodzaju pytania można łatwo odpowiedzieć za pomocą interpretera języka Python lub, w celu uzyskania większej liczby funkcji, powłoki IPython .
Jeśli chcesz przekazać metodę klasy jako argument, ale nie masz jeszcze obiektu, do którego chcesz ją wywołać, możesz po prostu przekazać obiekt, gdy masz go jako pierwszy argument (tzn. „Ja” argument).
class FooBar:
def __init__(self, prefix):
self.prefix = prefix
def foo(self, name):
print "%s %s" % (self.prefix, name)
def bar(some_method):
foobar = FooBar("Hello")
some_method(foobar, "World")
bar(FooBar.foo)
Spowoduje to wydrukowanie „Hello World”
Wiele dobrych odpowiedzi, ale dziwne, że nikt nie wspomniał o użyciu lambda
funkcji.
Więc jeśli nie masz argumentów, sprawy stają się dość trywialne:
def method1():
return 'hello world'
def method2(methodToRun):
result = methodToRun()
return result
method2(method1)
Ale powiedz, że masz jeden (lub więcej) argumentów w method1
:
def method1(param):
return 'hello ' + str(param)
def method2(methodToRun):
result = methodToRun()
return result
Następnie możesz po prostu wywołać method2
jako method2(lambda: method1('world'))
.
method2(lambda: method1('world'))
>>> hello world
method2(lambda: method1('reader'))
>>> hello reader
Uważam, że jest to o wiele czystsze niż inne odpowiedzi tutaj wymienione.
()
na końcu obiektu w swoim wywołaniu zwrotnym, duh.
Metody są obiektami jak każdy inny. Możesz je przekazywać, przechowywać na listach i dyktandach, robić z nimi co tylko zechcesz. Szczególną rzeczą w nich jest to, że są obiektami, które można wywoływać, więc możesz je wywoływać __call__
. __call__
jest wywoływany automatycznie, gdy wywołujesz metodę z argumentami lub bez, więc wystarczy napisać methodToRun()
.
Nie do końca to, czego chcesz, ale pokrewnym przydatnym narzędziem jest getattr()
użycie nazwy metody jako parametru.
class MyClass:
def __init__(self):
pass
def MyMethod(self):
print("Method ran")
# Create an object
object = MyClass()
# Get all the methods of a class
method_list = [func for func in dir(MyClass) if callable(getattr(MyClass, func))]
# You can use any of the methods in method_list
# "MyMethod" is the one we want to use right now
# This is the same as running "object.MyMethod()"
getattr(object,'MyMethod')()
foo
?