静态方法 - 如何从另一个方法调用一个方法?
Posted
技术标签:
【中文标题】静态方法 - 如何从另一个方法调用一个方法?【英文标题】:Static methods - How to call a method from another method? 【发布时间】:2010-12-24 00:23:19 【问题描述】:当我有常规方法可以调用类中的另一个方法时,我必须这样做
class test:
def __init__(self):
pass
def dosomething(self):
print "do something"
self.dosomethingelse()
def dosomethingelse(self):
print "do something else"
但是当我有静态方法时我不能写
self.dosomethingelse()
因为没有实例。在 Python 中从同一个类的另一个静态方法调用静态方法需要做什么?
【问题讨论】:
@pablo:你不能改变问题的本质!!结束这个问题并开始另一个问题!! 好的,好的。你的意思是删除问题?答案已经在 Peter Hansen 的评论中了 @pablo:你不能在这里删除,这对所有为你的问题提供答案的人来说都是不礼貌的。您需要接受答案并创建一个新问题。 @pablo:为了明确一点:您的原始问题表述应该被接受。别担心,你会在这里学习。干杯:-) 【参考方案1】:如何在 Python 中从同一类的另一个静态方法调用静态方法?
class Test() :
@staticmethod
def static_method_to_call()
pass
@staticmethod
def another_static_method() :
Test.static_method_to_call()
@classmethod
def another_class_method(cls) :
cls.static_method_to_call()
【讨论】:
调用Test.static_method_to_call()
也应该适用于该类的其他非静态和非类方法,对吧? (......可能还有其他课程?)
是的,Test.static_method_to_call()
可以在任何地方工作。【参考方案2】:
class.method
应该可以工作。
class SomeClass:
@classmethod
def some_class_method(cls):
pass
@staticmethod
def some_static_method():
pass
SomeClass.some_class_method()
SomeClass.some_static_method()
【讨论】:
这里应该补充一点建议:很明显classmethods相对于staticmethods没有缺点,而且classmethods允许将来扩展该方法以调用其他类方法。因此,它应该始终是首选,即使没有立即需要。 @u0b34a0f6ae:我不知道我做的好不好……但我在一个类中定义了一个装饰器。装饰器必须是“静态方法”,而不是“类方法”。 @u0b34a0f6ae 类方法总是线程安全的吗?在我的用例中,我在线程中使用静态方法来防止意外访问可能不是线程安全的类。 @u0b34a0f6ae always 有点强。例如,使用 PySpark 静态方法可以在 rdd 作业中使用,而类方法不能。【参考方案3】:注意 - 问题似乎有所改变。关于如何从静态方法调用实例方法的问题的答案是,您不能不将实例作为参数传入或在静态方法中实例化该实例。
以下主要是回答“如何从另一个静态方法调用静态方法”:
请记住,Python 中的静态方法和类方法之间存在 区别。静态方法不接受隐式的第一个参数,而类方法将类作为隐式的第一个参数(通常为cls
按照惯例)。考虑到这一点,您可以这样做:
如果是静态方法:
test.dosomethingelse()
如果是类方法:
cls.dosomethingelse()
【讨论】:
您只能在类定义中使用cls.dosomethingelse()
。
更准确地说,您只能在类方法本身中使用cls.dosomethingelse()
。就像您只能在实例方法本身中使用 self
。
对不起,我写错了问题。哎呀!我想写“我必须如何在 Python 中从同一类的另一个静态方法调用实例方法”而不是“如何在 Python 中从相同的另一个静态方法调用静态方法类”
@pablo:在这种情况下,你需要写另一个问题并完成这个问题。
@jldupont ,我已经有了答案,但在一条评论中。我该怎么办,因为我不能接受,但抹去这个问题会很浪费,不是吗?【参考方案4】:
好的,类方法和静态方法的主要区别是:
类方法有自己的标识,这就是为什么它们必须从一个实例中调用。 另一方面,静态方法可以在多个实例之间共享,因此必须从类中调用它【讨论】:
这似乎不对——但这里的意思是模糊的,没有例子,所以很难说。主要是,“类方法”不必“从一个实例中”调用……你可以从任何知道MyClass
的地方调用MyClass.class_method()
(也许你在想“实例方法”?)跨度>
【参考方案5】:
如果这些不依赖于类或实例,那么只需将它们设为函数即可。
因为这似乎是显而易见的解决方案。除非您当然认为它需要被覆盖、子类化等。如果是这样,那么以前的答案是最好的选择。祈祷我不会因为仅仅提供可能满足或不满足某人需求的替代解决方案而被贬低;)。
因为正确答案取决于相关代码的用例;)
【讨论】:
【参考方案6】:您不能从静态方法中调用非静态方法,而是通过在静态方法中创建实例来调用。
应该是这样的
class test2(object):
def __init__(self):
pass
@staticmethod
def dosomething():
print "do something"
# Creating an instance to be able to
# call dosomethingelse(), or you
# may use any existing instance
a = test2()
a.dosomethingelse()
def dosomethingelse(self):
print "do something else"
test2.dosomething()
【讨论】:
IMO 这种方法明显比仅使用@classmethod
声明您的方法,并在cls.dosomething()
中使用cls.dosomethingelse()
更糟糕——在性能方面更差(实例化对象只是为了访问一个静态方法)和可读性(这并不简单,我想如果这种模式成为样板,整个代码库对于人类来说可能会变得非常难以解析)
正如我在 SO 的其他地方读到的,与其直接初始化实例来调用方法,不如直接调用它 - 它会自行初始化。以上是关于静态方法 - 如何从另一个方法调用一个方法?的主要内容,如果未能解决你的问题,请参考以下文章