I am trying to learn how classes work. I would like to create different classes with some shared elements and others not, but as far as I know I can create it from three different ways:
Create a class with all the shared elements and then inherit this class and modify specific methods and attributes in the new class. Something like that:
class Enemy(object):
"""Enemy!"""
def __init__(self, damage=30, life=100, enemy="Hero"):
#And keep defining the class and its methods and attributes in common with all the enemys
class Troll(Enemy):
"""Troll!"""
def __init__ (self, defense=0):
#And define the specific attributes and methods for Trolls.
Create a class and ask for a type of class, and change the definition of the object from which input it got. Something like that:
class Enemy(object):
"""Enemy!"""
def __init__(self, damage=30, defense=0, life=100, type="Troll" enemy="Hero"):
if type=="Troll":
#Do that for type "Troll"
if type=="Goblin":
#Do that for type "Goblin"
#And keep defining the class and its methods and attributes for each accepted type
Create two different classes and then do multiple inheritance:
class Enemy(object):
"""Enemy!"""
def __init__(self, damage=30, life=100, enemy="Hero"):
#And keep defining the class and its methods and attributes in common with all the enemys
class Trolls(object):
"""Trolls!"""
def __init__ (self, defense=1, shield=20):
#And define the specific attributes and methods for Trolls.
class SuperTroll(Enemy, Trolls):
I see the first one is the easy one that let me be more flexible to create multiple classes with shared methods and attributes. But the second one seems to me more easy to use(or at least I like it), and I can get out of the if
conditionals whatever I want. And the third one could be practical for mixing different classes without any shared method or attribute, and if they share it wouldn't mess it (or it would?).
Which one is better?
But about writing in one or the other way it seems it is just a matter of strategy about how do you want your code. Is this correct?
The second example is not a good idea; it will lead to a lot of duplicated code, and you have to edit your Enemy
class every time you come up with a new type of enemy character.
Picking between the first and third is trickier, and will depend on what you want to achieve ("a matter of strategy", as you have it).
The first, single inheritance from Enemy
for Troll
and Goblin
, is useful because it allows you to define all the code that all Enemy
characters will have once, and only define the differences in the Troll
and Goblin
classes. You could extend this further, and have Enemy
inherit from a superclass (or metaclass) Character
, that provides the really basic stuff for both Enemy
and Hero
classes (e.g. name
, health
, ...).
class Enemy(Character)
class Troll(Enemy)
The third example may be useful if you want to separate characters and roles, e.g. you could have
class FriendlyTroll(Troll, Friend)
and
class UnfriendlyTroll(Troll, Enemy)
if those roles are going to mean different instance attributes (e.g. the Friend
mix-in might introduce a share
method). This allows for more complexity in your character definitions, but if you are not going to use the extra functionality it is a lot of complication to get your head around, and may lead to intractable multiple-inheritance problems.
TL;DR: Use the first one! If you decide later that you really need to separate out roles into mix-in classes, that isn't too complex a task.
First one:
Proper way to go...You are inheriting from what is collectively "ENEMY". Here you can have common things that "ENEMY" has under the class and have individual classes for all types of enemy and also you can well override some of the methods that makes some kind of "ENEMY" distinct.
Second one:
Not nice or properly object oriented because what if "trolls" have some property that is not shared by other "enemy". You might say that it can go under "if" statement you have but this makes the code very-less manageable which is why you use OOP ( to manage the code, it's not all but one of the reason).
Third one:
I strongly suggest not using multiple-inheritance as far as possible. Google diamond death problem and you will know why. One rule for multiple-inheritence--"If you think you need multiple inheritance, you are probably wrong. If you know you have to use multiple inheritance, you are probably right."
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With