python中的类常量

问题:python中的类常量

在python中,我希望一个类具有一些在所有子类中通用的“常量”(实际上是变量)。有没有办法用友好的语法做到这一点?现在我使用:

class Animal:
    SIZES=["Huge","Big","Medium","Small"]

class Horse(Animal):
    def printSize(self):
        print(Animal.SIZES[1])

我想知道是否有更好的方法或者不用写“动物”就能做到。之前的大小。谢谢!编辑:忘记提及马从动物继承。

In python, I want a class to have some “constants” (practically, variables) which will be common in all subclasses. Is there a way to do it with friendly syntax? Right now I use:

class Animal:
    SIZES=["Huge","Big","Medium","Small"]

class Horse(Animal):
    def printSize(self):
        print(Animal.SIZES[1])

and I’m wondering if there is a better way to do it or a way to do it without then having to write “Animal.” before the sizes. Thanks! edit: forgot to mention that horse inherits from animal.


回答 0

由于Horse是的子类Animal,您可以更改

print(Animal.SIZES[1])

print(self.SIZES[1])

不过,您仍然需要记住这SIZES[1]意味着“大”,因此您可以通过执行以下操作来改进代码:

class Animal:
    SIZE_HUGE="Huge"
    SIZE_BIG="Big"
    SIZE_MEDIUM="Medium"
    SIZE_SMALL="Small"

class Horse(Animal):
    def printSize(self):
        print(self.SIZE_BIG)

或者,您可以创建中间类:HugeAnimalBigAnimal等等。如果每个动物类别都包含不同的逻辑,那将特别有用。

Since Horse is a subclass of Animal, you can just change

print(Animal.SIZES[1])

with

print(self.SIZES[1])

Still, you need to remember that SIZES[1] means “big”, so probably you could improve your code by doing something like:

class Animal:
    SIZE_HUGE="Huge"
    SIZE_BIG="Big"
    SIZE_MEDIUM="Medium"
    SIZE_SMALL="Small"

class Horse(Animal):
    def printSize(self):
        print(self.SIZE_BIG)

Alternatively, you could create intermediate classes: HugeAnimal, BigAnimal, and so on. That would be especially helpful if each animal class will contain different logic.


回答 1

您可以SIZES通过self.SIZES(在实例方法中)或cls.SIZES(在类方法中)到达。

无论如何,您都必须明确说明在哪里可以找到SIZES。一种替代方法是将SIZES包含类的模块放入,但随后您需要在单个模块中定义所有类。

You can get to SIZES by means of self.SIZES (in an instance method) or cls.SIZES (in a class method).

In any case, you will have to be explicit about where to find SIZES. An alternative is to put SIZES in the module containing the classes, but then you need to define all classes in a single module.


回答 2

class Animal:
    HUGE = "Huge"
    BIG = "Big"

class Horse:
    def printSize(self):
        print(Animal.HUGE)
class Animal:
    HUGE = "Huge"
    BIG = "Big"

class Horse:
    def printSize(self):
        print(Animal.HUGE)

回答 3

扩展betabandido的答案,您可以编写一个函数将属性作为常量注入模块:

def module_register_class_constants(klass, attr_prefix):
    globals().update(
        (name, getattr(klass, name)) for name in dir(klass) if name.startswith(attr_prefix)
    )

class Animal(object):
    SIZE_HUGE = "Huge"
    SIZE_BIG = "Big"

module_register_class_constants(Animal, "SIZE_")

class Horse(Animal):
    def printSize(self):
        print SIZE_BIG

Expanding on betabandido’s answer, you could write a function to inject the attributes as constants into the module:

def module_register_class_constants(klass, attr_prefix):
    globals().update(
        (name, getattr(klass, name)) for name in dir(klass) if name.startswith(attr_prefix)
    )

class Animal(object):
    SIZE_HUGE = "Huge"
    SIZE_BIG = "Big"

module_register_class_constants(Animal, "SIZE_")

class Horse(Animal):
    def printSize(self):
        print SIZE_BIG