0

I'm sure this is a duplicate, but I can't track it down at the moment.

In this example, why is self not defined?

class State(Enum):
    MY_STATE = type(self)('foo', 'bar')

    def __init__(self, some, thing):
        self.some = some
        self.thing = thing

Replacing type(self) with State also returns a NameError but for State.

MTCoster
  • 5,868
  • 3
  • 28
  • 49

2 Answers2

2

self is not defined, because you refer to it in a class variable, not an instance variable. It is similar to using this in a static method in another language. The same for State, at the point you refer to it, the class has not been defined yet and the name doesn't exist.

blue_note
  • 27,712
  • 9
  • 72
  • 90
  • what does "refer to it in a class variable" mean? Could you elaborate? – MSeifert Oct 17 '17 at 10:16
  • Does this make it impossible to have an instance variable of type `State`? – MTCoster Oct 17 '17 at 10:16
  • That would go into infinite recursion anyway because the instance variable would itself create an instance variable, which would create an instance variable .... – MSeifert Oct 17 '17 at 10:16
  • How would you go about achieving something like [Java's Enums](https://docs.oracle.com/javase/tutorial/java/javaOO/enum.html)? – MTCoster Oct 17 '17 at 10:17
  • You can create an instance variable inside your `__init__`. `self` exists inside it (it is autotically passed as argument). but be careful of infinite recursion. – blue_note Oct 17 '17 at 10:18
  • @MTCoster: See the first code example at https://docs.python.org/3/library/enum.html for java-like enumeration – blue_note Oct 17 '17 at 10:19
  • @MTCoster That depends on what exact feature you want from the Java enum. The basic one doesn't need an `__init__` or some instance variables at all. – MSeifert Oct 17 '17 at 10:20
  • The difference I'm seeing is that in Java, the elements are effectively instances of the enum class whereas Python uses a separate type for the elements – MTCoster Oct 17 '17 at 10:20
  • I'm not sure what you mean. In both python and java, the fields of an enumeration are just names for integer values. – blue_note Oct 17 '17 at 10:25
1

Why not extract another class like this:

from enum import Enum


class MyClass:
    def __init__(self, some, thing):
        self.some = some
        self.thing = thing


class State(Enum):
    MY_STATE = MyClass('foo', 'bar')


print(State.MY_STATE == State.MY_STATE)
Menglong Li
  • 2,177
  • 14
  • 19