I was reading this wiki article about composition over inheritance and in the example they used an abstract class. Let's say you wanted to avoid they use of abstract classes completely and only use concrete classes. I want to know, is my example a proper use of composition. Let's say I have the following IGameobject interface.
public interface IGameObject
{
string Name {get;}
}
and the follwing weapon interface:
//Note the IGameObject getter
public interface IWeapon
{
int Damage {get; }
IGameObject gameObject {get;}
}
Normally, in my game, a weapon is-a IGameObject. However, considering that we're using composition, according to the wiki article it's a has-a relationship.
Now, I could do this when creating a Sword object:
public class Sword : IWeapon
{
private IWeapon weaponObject;
public Sword(IWeapon weapon)
{
this.weaponObject = weapon;
}
public int Damage
{
get
{
return this.weaponObject.Damage;
}
}
public IGameObject gameObject
{
get
{
return this.weaponObject.gameObject;
}
}
}
I can now store my sword in a collection, for example, a List:
List<IWeapon> weapons = new List<IWeapon>();
weapons.add(swordObj)
and still have access to my IGameObject.
Now, I have a 3 questions:
IGameObject
interface?IGameObject getter
? (The reason is, if I store it as an IWeapon, with no IGameObject getter, how then would I get the details of the IGameObject
?)Composition vs. Inheritence is a very important principle to grasp, however, like any principle, it has a positive effect only if properly applied. In order to properly apply it, you must understand how it came to light.
C vs I was thought of because developers 'went to town' on OOP, especially in languages like C++ where multiple inheritance is allowed. Everything went downhill pretty quickly, design-wise, as you can imagine.
It is easy to think of this principle in the following manner: We as OOD system designers wish to model domain object relationships in a manner which most resembles the domain we would like to mimic- therefore we need to look at these relationships closely and carefully.
Whenever you are about to inherit, do consider whether or not inheritance closely describes the real world relationship between the entities in question.
In your case, a weapon is infact a game object, so inheriting is actually a good idea and will promote polymorphism along the way.
Here is an example of how C vs I may apply in your domain:
interface IGameCharacter
{
ICollection<IWeapon> Weapons {get;}
ICollection<IGameCharacter> Party {get;}
}