Step 1 of 7 · Reading · ~3 min
Learn
Inheritance, Interfaces, and Exceptions
Inheritance and virtual/override
By the end of this lesson you can build a class on top of another, change inherited behavior with virtual and override, and make one variable of a base type run different code depending on the object it holds.
Inheritance models an is-a relationship: a Dog is an Animal. The child class (derived class) gets the parent's (base class) members and can add or change some. C# classes have exactly one base class. Use inheritance only for genuine is-a relationships; for anything else, prefer holding another object as a field.
Basic inheritance and base
class Animal {
public string Name { get; private set; }
public Animal(string name) { Name = name; }
public virtual string Speak() {
return Name + " makes a sound";
}
}
class Dog : Animal {
public Dog(string name) : base(name) { }
public override string Speak() {
return Name + " barks";
}
}
{ get; private set; }- anyone can readName, but only code insideAnimalitself can change it.class Dog : Animal- the colon names the base class.: base(name)- the child's constructor must call a parent constructor, passing it what it needs. If you omit it, the parent needs a parameterless constructor or the code will not compile.virtualmarks a parent method that children may replace;overrideis how a child replaces it. Methods in C# are not virtual by default.- Inside an override,
base.Speak()calls the parent's version, so a child can extend behavior instead of rewriting it:return base.Speak() + ", loudly";.
Polymorphism
A variable of the base type can hold any derived object, and a call to a virtual method runs the most derived version:
Animal[] zoo = { new Animal("Generic"), new Dog("Rex") };
foreach (Animal a in zoo) {
Console.WriteLine(a.Speak()); // Generic makes a sound, then Rex barks
}
The loop is written once against Animal and works for every future subclass. That is the point of inheritance.
abstract classes
An abstract class cannot be instantiated and may declare abstract methods with no body, which every concrete child must override:
abstract class Shape {
public abstract int Sides();
public string Describe() { return "a shape with " + Sides() + " sides"; }
}
class Triangle : Shape {
public override int Sides() { return 3; }
}
new Shape() is a compile error; new Triangle().Describe() works, and it calls the child's Sides(). An override method can itself be overridden by a further child unless you mark it sealed override (or the whole class sealed).
The trap: new hides, override replaces
class Cat : Animal {
public Cat(string name) : base(name) { }
public new string Speak() { return Name + " meows"; } // hides, does not override
}
Animal pet = new Cat("Tom");
Console.WriteLine(pet.Speak()); // Tom makes a sound -- the base version ran!
new on a method creates a separate method with the same name. Through a base-typed variable, the base version is called. The compiler warns when you forget either keyword. Use override.
protected members are visible to the class and its children but not to outside code; private members are visible only inside the class itself, even to children.
Common mistakes
- Forgetting
virtualon the parent method, sooverridedoes not compile. - Using
newinstead ofoverride, which silently breaks polymorphism. - Forgetting
: base(...)when the parent has no parameterless constructor. - Repeating the parent's logic in the child instead of calling
base.Method(); then a later fix to the parent misses the child.
Your exercise
The starter gives you the abstract base class and the loop that reads each line. Write the child classes and use them through the base type, as the exercise describes. The most likely mistake is a child class that copies the parent's calculation instead of calling base, or a call made through the child type instead of the base type.
Discussion
Ask a question, share an insight, or help someone who’s stuck.
Sign in to post a comment or reply.
Loading…