简体   繁体   English

如何在抽象类中调用非抽象方法?

[英]How to call non abstract method in a abstract class?

I have an abstract class in python and want to call non-abstract methods in it. 我在python中有一个抽象类,想在其中调用非抽象方法。 Is it possible to do it? 有可能做到吗?

from abc import ABC, abstractmethod
class MyAbstract(ABC):

# Can I call method get_state() from get_current() ?
def get_state():
   get_current()  # gives me error?

def get_current():

@abstractmethod
def get_time():

I have another python file, Temp.py implement this interface. 我还有另一个python文件,Temp.py实现此接口。 In Temp.py, I call the get_state using MyAbstract.get_state() , I get the error stating that get_current() is undefined. 在Temp.py中,我使用MyAbstract.get_state()调用get_state ,但出现错误,指出get_current()未定义。

Not sure why. 不知道为什么。

Any help is appreciated. 任何帮助表示赞赏。

In general, all methods have a namespace which is the class or object they're attached to. 通常,所有方法都有一个名称空间,该名称空间是它们所附加的类或对象。 If you have an instance of a class floating around (eg self , most of the time), you can call methods on that instance that automatically pass the instance itself as the first parameter - the instance acts as the namespace for an instance method . 如果您有一个浮动的类的实例(例如,大多数时候是self ),则可以在该实例上调用自动将实例本身作为第一个参数传递的方法- 该实例充当实例方法的名称空间

If you're using a class method or a static method, then the namespace is almost always going to be the class they're attached to. 如果您使用的是类方法或静态方法,则名称空间几乎总是会成为它们所附加的类。 If you don't specify a namespace, then python assumes that whatever function you're trying to call is in the global namespace, and if it isn't, then you get a NameError . 如果未指定名称空间,则python会假定您要调用的任何函数都在全局名称空间中,否则,您会得到NameError

In this case, the following should work for you: 在这种情况下,以下应为您工作:

class MyAbstract(ABC):
    def get_current():
        print("current")

    def get_state():
        MyAbstract.get_current()

    @abstractmethod
    def get_time():
        pass

You can just imagine that you have a little invisible @staticmethod decorator hanging above get_current() that marks it as such. 您可以想象一下,在get_current()上方悬挂了一个不可见的@staticmethod装饰器,将其标记为此类。 The problem with this is that now you don't get to change the behavior of get_current() in subclasses to affect change in get_state() . 问题在于,现在您不必更改子类中的get_current()的行为来影响get_state()更改。 The solution to this is to make get_state() a class method: 解决方案是使get_state()为类方法:

    @classmethod
    def get_state(cls):
        cls.get_current()

Calling a static method uses identical syntax to calling a class method (in both cases you would do MyAbstract.get_state() , but the latter passes the class you're calling it on as the first argument. You can then use this class as a namespace to find the method get_current() for whatever subclass has most recently defined it, which is how you implement polymorphism with method that would otherwise be static. 调用静态方法的语法与调用类方法的语法相同(在两种情况下,您都将执行MyAbstract.get_state() ,但后者将您正在调用作为第一个参数传递给 。然后,您可以将该类用作命名空间,用于为子类最近定义的任何方法找到方法get_current() ,这是您如何使用本来是静态的方法实现多态的方法。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM