Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

How to get in a superclass full names of all methods in subclasses that start with the same two letters in python

I have number of subclasses all of which have number of methods whose names start with "on.."
eg.:

def on_index(self):
    raise NotImplementedError()

def on_spiking_intent(self):
    raise NotImplementedError()

def on_no_option(self):
    raise NotImplementedError()

I would like to write a method in the superclass which prints a list of all the "on…" methods of its subclasses and specifies to which subclass the method belongs.

I guess this get_all_on_methods method need not be in the superclass, but it made sense to me to put it there as only the superclass unites the subclasses.

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

How should I go about this? I was thinking about somehow using decorators like putting

@onmethod

in front of every "on…" method or also somehow using an abstract class. But I actually don’t know.

>Solution :

You can iterate over the subclasses of some class using the __subclasses__() method. You can check the namespace of the subclasses for attributes that start with "on_", so something to the effect of:

class Ur:
    @classmethod
    def get_all_on_methods(cls):
        results = []
        for klass in cls.__subclasses__():
            for name, attribute in vars(klass).items():
                if name.startswith("on_"):
                    results.append((attribute, klass))
        return results

class Foo(Ur):
    def on_index(self):
        pass
    def some_method(self):
        pass

class Bar(Ur):
    def on_spiking_intent(self):
        pass
    def another_method(self):
        pass

This populates a list for illustration purposes, you could easily populate a dictionary or whatever you want instead.

Also, this gets any class attribute, so you might want to check if it is a method by using:

if callable(attribute) and name.startswith("on_"):
    ...

But that is up to you.

Here’s the output you get in the above example:

In [2]: Ur.get_on_methods()
Out[2]:
[(<function __main__.Foo.on_index(self)>, __main__.Foo),
 (<function __main__.Bar.on_spiking_intent(self)>, __main__.Bar)]
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading