简体   繁体   中英

How to get attributes in the order they are declared in a Python class?

As described in PEP435 , an enum can be defined this way:

class Color(Enum):
    red = 1
    green = 2
    blue = 3

And the resulting enum members of Color can be iterated in definition order: Color.red, Color.green, Color.blue .

This reminds me of Form in Django , in which fields can be rendered in the order they are declared in a Form subclass. They implemented this by maintaining a field counter, every time a new field is instantiated the counter value get incremented.

But in the definition of Color , we don't have something like a FormField , how can we implement this?

In Python 3, you can customize the namespace that a class is declared in with the metaclass. For example, you can use an OrderedDict :

from collections import OrderedDict

class EnumMeta(type):

    def __new__(mcls, cls, bases, d):
        print(d)
        return type.__new__(mcls, cls, bases, d)

    @classmethod
    def __prepare__(mcls, cls, bases):
        return OrderedDict()


class Color(metaclass=EnumMeta):
    red = 1
    green = 2
    blue = 3

This prints

OrderedDict([('__module__', '__main__'), ('red', 1), ('green', 2), ('blue', 3)])

In Python 2.x you can use this horrible hack I wrote to answer a slightly different question, as a foundation for functionality of this sort. So, really, you can't. :-)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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