Home > Enterprise >  Class not directly inheriting but can use method from another class
Class not directly inheriting but can use method from another class

Time:01-24

I came accross a piece of Python legacy code at work that I couldn't understand how it could work without errors. Obviously I can't write the exact code here but here is a minimal working example:

class ClassB:
    def func(self, txt: str):
        return self.str_to_uppercase(txt)


class ClassA(ClassB):
    def str_to_uppercase(self, txt: str):
        return txt.upper()


if __name__ == "__main__":
    my_instance = ClassA()
    print(my_instance.func("Hello, World!"))

stdout: HELLO, WORLD!

What's strange to me is that, although ClassB is not directly inheriting from ClassA where the instance method str_to_uppercase() is defined, ClassB is still able to call this method. I should also note that my linter (pylint) is complaining that str_to_uppercase() is not defined in ClassB. So I'm struggling to understand how the mechanics of the code works here regarding inheritence.

Secondly, this code looks strange to me. It doesn't seem very "Pythonic". So, as a second question, I was wondering in which usecases such code is useful?

CodePudding user response:

This is quite standard in OO and even has a name: The Template Method Pattern.

The idea is that ClassB should define some useful functionality, but only at a high level. Its code calls other methods that it doesn't define, but still depends on.

This leaves other classes (ClassA in your example) to provide the fine details, called implementation details.

CodePudding user response:

When a method is called on an object, Python accesses the list of defined methods of the actual class of the object. Inside the ClassB.func(self,...) method, the actual class of the self object is ClassA. ClassA has a str_to_uppercase() so it can be called even though this code is part of ClassB (which doesn't need to know ClassA).

If you passed my_instance to any regular function that expects an object as parameter, you would be able to call the str_to_uppercase() method of that object within the function (and that would not be a surprise). The name self in method definitions is actually just a convention for the first parameter of the function which is implicitly the instance of the object calling it.

  • Related