Skip to content Skip to sidebar Skip to footer

Calling The Setter Of A Super Class In A Mixin

Suppose I have the following (not quite biologically correct) classes: class AnimalBaseClass: def __init__(self): self._limbs = None @property def limbs(self):

Solution 1:

The following works, although any simpler answers are appreciated.

class AnimalBaseClass:
    def __init__(self):
        self._limbs = None

    @property
    def limbs(self):
        return self._limbs

    @limbs.setter
    def limbs(self, value):
        self.paws = value
        self._limbs = value


class BipedalMixIn:
    @property
    def limbs(self):
        return super().limbs

    @limbs.setter
    def limbs(self, value):
        self.bipedal = (value == 2)
        # works!
        super(BipedalMixIn, self.__class__).limbs.__set__(self, value)


class Bird(BipedalMixIn, AnimalBaseClass):
    pass


bird = Bird()
bird.limbs = 2
print(bird.bipedal)    # True
print(bird.paws)        # 2

Solution 2:

Firstly, if you're working under Python 2.x, make sure all of your classes directly or indirectly inherit from object. Otherwise, @property does not work at all.

To steal the example code from this comment in OP's linked bug:

super(BipedalMixin, BipedalMixin).limbs.__set__(self, value)

Let's break this apart:

super(BipedalMixin, BipedalMixin)

Normally, we pass an instance as the first argument. Here, we're instead passing a class, to look up class attributes specifically and disable any descriptor magic.

.limbs.__set__(self, value)

This invokes the property's __set__() method, which calls the setter. It is normally invoked automatically by the foo.limbs = bar syntax.


Post a Comment for "Calling The Setter Of A Super Class In A Mixin"