Friday, April 21, 2023

A bit of fun with Jabberwocky, classes, mixins, python3's super() and method resolution order (MRO)

I was trying to figure out and demonstrate python's Member Resolution Order... In particular, pay attention to the output from __str__...

 ¢ in a previous post I'd done the same, but in py2. ¢

#!/usr/bin/env python
# -*- coding: utf-8 -*-

class BeastBase(dict):
def __init__(self, **characteristics):
super().__init__(**characteristics)

def __str__(self):
return "; ".join(["%s=%r"%item for item in super().items()])

class Mixin(object): pass

class BitingMixin(Mixin):
def __init__(self, jaws=2, teeth_per_mouth=32, **characteristics):
self.jaws=jaws
self.teeth_per_mouth=teeth_per_mouth
super().__init__(**characteristics)

def bite(self):
print("Bite: jaws=%s, teeth=%s"%(self.jaws, self.teeth_per_mouth*self.jaws/2))

def __str__(self):
return "Jawed: %s; %s"%(self.jaws, super().__str__())

class JawedBeast(BeastBase, BitingMixin): pass

class ClawingMixin(Mixin):
def __init__(self, feet=4, toes_per_foot=3, **characteristics):
self.feet=feet
self.toes_per_foot=toes_per_foot
super().__init__(**characteristics)

def catch(self):
print("Catch: feet=%s, toes=%s"%(self.feet, self.toes_per_foot*self.feet))

def __str__(self):
return("Claws: %s; %s"%(self.toes_per_foot*self.feet, super().__str__()))

class ClawedBeast(BeastBase, ClawingMixin): pass

class FlamingMixin(Mixin):
def __init__(self, eyes=6, flames_per_eye=1, **characteristics):
self.eyes=eyes
self.flames_per_eye=flames_per_eye
super().__init__(**characteristics)

def flame(self):
print("Flames:", self.eyes*self.flames_per_eye)

def __str__(self):
return("Eyes: %s, Flames: %s; %s"%(self.eyes, self.eyes*self.flames_per_eye, super().__str__()))

class FlamedBeast(FlamingMixin, BeastBase): pass

class WhifflingMixin(Mixin):
def whiffle(self):print ("Whiffle....")
def __str__(self): return "Whiffling... "+super().__str__()

class WhifflingBeast(WhifflingMixin, BeastBase): pass

class BurblingMixin(Mixin):
def burble(self): print("Burble....")
def __str__(self): return "Burbling... "+super().__str__()

class BurblingBeast(BurblingMixin, BeastBase): pass

class Jabberwocky(BitingMixin, ClawingMixin, FlamingMixin, WhifflingMixin, BurblingMixin, BeastBase):
def __init__(self, **characteristics):
super().__init__(**characteristics)

def __str__(self):
return "JabberWocky: "+super().__str__()+" ... Beware! "

if __name__ == "__main__":

# Beware the Jabberwock, my son!
jabberwocky1=Jabberwocky(personality="Friendly", consideration="Temperamental", eyes=5, flames_per_eye=3)
print(jabberwocky1)

# Beware the Jubjub bird, and shun
# The frumious Bandersnatch!

# The jaws that bite, the claws that catch!
jabberwocky1.bite()
jabberwocky1.catch()

# And as in uffish thought he stood,
# The Jabberwock, with eyes of flame,
jabberwocky1.flame()

# Came whiffling through the tulgey wood,
jabberwocky1.whiffle()
# And burbled as it came!
jabberwocky1.burble()

Output: ¢ In particular, pay attention to the output from __str__... ¢

JabberWocky: Jawed: 2; Claws: 12; Eyes: 5, Flames: 15; Whiffling... Burbling... personality='Friendly'; consideration='Temperamental' ... Beware!
Bite: jaws=2, teeth=32.0
Catch: feet=4, toes=12
Flames: 15
Whiffle....
Burble....

 

No comments:

Post a Comment