2

So I have my base class:

class Foo():
    pass

I'm never going to instantiate this class - I just want it as a custom namespace. One of the things I want from it is its name:

>>> Foo.__name__
'Foo'

But I want to change the interface to this, so that there's no underscores. Getting the name of the class from the class object is going to happen a lot, so it should be cleaner:

class Foo:
    def name():
        return Foo.__name__

This works great! Oh, except I have the name "Foo" hard coded. I might as well just have it return a string. That's not good enough, because I need to inherit this adjustment:

class Bar(Foo):
   pass

>>> Bar.name()
'Foo'

No bueno.

Basically, I need a class function that returns the name of the class, and which will still work when inherited. I can't use self because I'm not making instances. Is there anything which will achieve a similar result? Do functions know about the namespace they are called from? If I really need to use objects I will, but for my purposes that will be uglier than a simple class hierarchy.

EDIT: I do not not believe this question is the same as the one it has been linked with. The solutions provided to the other question - mainly invoking the .__class__ attribute - would not work as an answer to this question because in my example I explicitly avoid instantiating objects. Also, the best answer provided here (using the @classmethod decorator to get the class object as a "self"-esque arg) appears nowhere in the linked alternative. Also, I believe my question to be framed in a clearer and more basic way than its purported duplicate. The same goes for the answer chosen.

1 Answers1

4

Just make it a class method with @classmethod and return the name of the class that's passed in:

class Foo:
    @classmethod
    def name(cls):
        return cls.__name__

class Bar(Foo): pass

This returns the correct name in each case:

>>> Foo.name()
'Foo'
>>> Bar.name()
'Bar'
Dimitris Fasarakis Hilliard
  • 150,925
  • 31
  • 268
  • 253