+When initializing an instance of the class in the class' __init__
method, calls tha are made using the instance may receive an instance of the class that is not
+yet fully initialized. When a method called in an initializer is overridden in a subclass, the subclass method receives the instance
+in a potentially unexpected state. Fields that would be initialized after the call, including potentially in the subclass' __init__
method,
+will not be initialized. This may lead to runtime errors, as well as make the code more difficult to maintain, as future changes may not
+be aware of which fields would not be initialized.
+
If possible, refactor the initializer method such that initialization is complete before calling any overridden methods.
+For helper methods used as part of initialization, avoid overriding them, and instead call any additional logic required
+in the subclass' __init__
method.
+
+If the overridden method does not depend on the instance self
, and only on its class, consider making it a @classmethod
or @staticmethod
instead.
+
+If calling an overridden method is absolutely required, consider marking it as an internal method (by using an _
prefix) to
+discourage external users of the library from overriding it and observing partially initialized state, and ensure that the fact it is called during initialization
+is mentioned in the documentation.
+
In the following case, the __init__
method of Super
calls the set_up
method that is overridden by Sub
.
+This results in Sub.set_up
being called with a partially initialized instance of Super
which may be unexpected.
In the following case, the initialization methods are separate between the superclass and the subclass.
+
-When an instance of a class is initialized, the super-class state should be
-fully initialized before it becomes visible to the subclass.
-Calling methods of the subclass in the superclass' __init__
-method violates this important invariant.
-
Do not use methods that are subclassed in the construction of an object.
-For simpler cases move the initialization into the superclass' __init__
method,
-preventing it being overridden. Additional initialization of subclass should
-be done in the __init__
method of the subclass.
-For more complex cases, it is advisable to use a static method or function to manage
-object creation.
-
Alternatively, avoid inheritance altogether using composition instead.
- -