C# Inheritance

  • Inheritance is one of the key functions in object oriented programming and it improves the modularity and performance.
  • Inheritance can separate a complex big project into a branches of simple classes and some of them can inherit part of functions of the others instead of writing everything from scratch.
  • When a new class inherits from an existed class, the new class is called derived class and the existed class is called base class.
  • The derived class inherits non-private members excluding constructors and destructors from the base class without rewriting them again if they are the same.
  • The derived class also can add its specific fields and methods to expand the functionality.
Note Note
The private members of the base class cannot be inherited by the derived class.

Because private members can only be accessed in the class in which it defines.

The syntax of class inheritance likes below. Putting the BaseClass behind the colon stands for the DerivedClass inherits from the BaseClass.

<Access Modifier> class <BaseClass>
{
    ......
}

<Access Modifier> class <DerivedClass> : <BaseClass>
{
    ......
}

The class inheritance hierarchy is shown as follows.

Class Inheritance Hierarchy

As you can see the above, Staff and Student inherit from Person, Teacher and Cleaner inherit from Staff.

Example 01-53-01

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
using System;

namespace TestInheritance
{
    public class Person
    {
        public string name;

        public void outName()
        {
            Console.Write("Name: {0}", this.name);
        }
    }

    public class Staff : Person
    {
        public int salary;

        public void outStaff()
        {
            this.outName();
            Console.Write("\tSalary: ${0}", this.salary);
        }
    }

    public class Student : Person
    {
        public byte grade = 1;

        public void outStudent()
        {
            this.outName();
            Console.WriteLine("\tGrade: {0}", this.grade);
        }
    }

    public class Teacher : Staff
    {
        public int teachTime;

        public void outTeacher()
        {
            this.outStaff();
            Console.WriteLine("\tTeach Time: {0}hrs", this.teachTime);
        }
    }

    public class Cleaner : Staff
    {
        public string cleanArea;

        public void outCleaner()
        {
            this.outStaff();
            Console.WriteLine("\tClean Area: {0}", this.cleanArea);
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            Teacher t = new Teacher();
            t.name = "Ben";
            t.salary = 3000;
            t.teachTime = 500;
            t.outTeacher();

            Cleaner c = new Cleaner();
            c.name = "David";
            c.salary = 1500;
            c.cleanArea = "Play Ground";
            c.outCleaner();

            Student s = new Student();
            s.name = "Steven";
            s.grade = 3;
            s.outStudent();

            Console.Read();
        }
    }
}

Output

Name: Ben	Salary: $3000	Teach Time: 500hrs
Name: David	Salary: $1500	Clean Area: Play Ground
Name: Steven	Grade: 3

Explanation

  • Line 5-13: Define a public class Person with a field and a method.
  • Line 15-24: Define a class Staff inherits from Person. Also a new field and a method are defined in the class.
  • Line 17: Declare a new field salary in the Staff class.
  • Line 19-23: Define a new method outStaff to output name and salary.
  • Line 26-35: Define a class Student inherits from Person.
  • Line 28: Declare a new field grade in the Student class.
  • Line 30-34: Define a new method outStudent to output name and grade.
  • Line 37-46: Define a class Teacher inherits from Staff.
  • Line 39: Declare a new field teachTime in the Teacher class.
  • Line 30-34: Define a new method outTeacher to output name, salary and teachTime.
  • Line 48-57: Define a class Cleaner inherits from Staff.
  • Line 50: Declare a new field cleanArea in the Cleaner class.
  • Line 52-56: Define a new method outCleaner to output name, salary and cleanArea.
  • Line 59-82: Define a class Program for testing.
  • Line 61: Main method starts here.
  • Line 63-67: Create an instance of Teacher, assign values to the fields and run the method outTeacher().
  • Line 69-73: Create an instance of Cleaner, assign values to the fields and run the method outCleaner().
  • Line 75-78: Create an instance of Student, assign values to the fields and run the method outStudent().

Example 01-53-02

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
using System;

namespace TestInheritance2
{
    public class Pet
    {
        private string name;

        public Pet() : this("None")
        {
        }

        public Pet(string name)
        {
            this.setName(name);
        }

        public void setName(string name)
        {
            this.name = name;
        }

        public void outName()
        {
            Console.Write("Name: {0}", this.name);
        }
    }

    public class Dog : Pet
    {
        public bool isBark;

        public Dog(bool isBark)
        {
            this.isBark = isBark;
        }

        public void outDog()
        {
            this.outName();
            Console.WriteLine("\tBark: {0}", this.isBark);
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            Dog d = new Dog(true);
            d.outDog();
            d.setName("Rocky");
            d.isBark = false;
            d.outDog();

            Console.Read();
        }
    }
}

Output

Name: None	Bark: True
Name: Rocky	Bark: False

Explanation

  • Line 5-27: Define a public class Pet.
  • Line 7: Declare a private string field name.
  • Line 9-11: Define the default constructor by calling this("None"). this("None") means Person("None") so it is calling another constructor with a parameter defined in line 13-16.
  • Line 13-16: Define a constructor with one parameter.
  • Line 15: Call setName() method and transfer the name's value as an argument.
  • Line 18-21: Define the method setName().
  • Line 20: The parameter's value is assigned to the field.
  • Line 23-26: Define the method outName() to output the value of the private field.
  • Line 29-43: Define a class Dog inherits from Pet.
  • Line 31: Declare a new boolean field isBark.
  • Line 33-36: Define a constructor with a parameter in class Dog. The field's value is assigned with the value of the parameter.
  • Line 40: Call the inherited method outName() which was defined in the class Pet.
  • Line 41: Output the value of isBark.
  • Line 45-57: Define a class Program for testing.
  • Line 47: Main method starts here.
  • Line 49: Instantiate the class Dog and transfer true to the constructor with one parameter.
  • Line 50: Run the outDog() method.
  • Line 51: Call the inherited method setName to set false to the value of the inherited field.
  • Line 53: Run the outDog() method to output the result.

If the default constructor of Pet were removed, you would get the following error.

'TestInheritance2.Pet' does not contain a constructor that takes 0 arguments

When an instance of the derived class Dog is created, the default constructor of the base class Pet will be called automatically. If there is no other constructor defined in Pet, a default constructor will be generated automatically. Because a constructor with a parameter was defined already in line 13-16 in Pet, the default constructor could not be generated. Then you got the error message.