C#
Inheritance
Parent Method
Child Class
Object-Oriented Programming

Call parent method from child class c

Master System Design with Codemia

Enhance your system design skills with over 120 practice problems, detailed solutions, and hands-on exercises.

Introduction

In C sharp inheritance, a child class can call parent behavior with the base keyword. The syntax is simple, but design choices around call order and override policy determine whether your class hierarchy stays reliable. A good implementation treats parent calls as contract decisions, not just syntax tricks.

Basic Parent Call with base

A child class overrides a virtual method and invokes parent implementation using base.MethodName(...). This is the standard extension pattern when parent logic must still run.

csharp
1using System;
2
3public class DocumentProcessor
4{
5    public virtual void Process(string id)
6    {
7        if (string.IsNullOrWhiteSpace(id))
8            throw new ArgumentException("id is required");
9
10        Console.WriteLine($"Base process: {id}");
11    }
12}
13
14public class SignedDocumentProcessor : DocumentProcessor
15{
16    public override void Process(string id)
17    {
18        base.Process(id);
19        Console.WriteLine($"Child signature step: {id}");
20    }
21}
22
23class Program
24{
25    static void Main()
26    {
27        DocumentProcessor p = new SignedDocumentProcessor();
28        p.Process("INV-42");
29    }
30}

This preserves parent validation and adds child-specific behavior.

Call Order Matters

Parent-first and parent-last are not equivalent. The right order depends on invariant ownership.

Use parent-first when base method enforces validation, setup, or authorization preconditions. Use parent-last when base method emits finalization behavior such as audit or cleanup that must include child changes.

If order is important, document it in code comments or method contract docs. Otherwise, future overrides may accidentally break lifecycle expectations.

Constructor Chaining Is Parent Invocation Too

Calling parent from child also applies to constructors with : base(...). This is required when parent has no default constructor or needs mandatory arguments.

csharp
1using System;
2
3public class UserBase
4{
5    public string Name { get; }
6
7    public UserBase(string name)
8    {
9        Name = name;
10        Console.WriteLine($"Base created for {Name}");
11    }
12}
13
14public class AdminUser : UserBase
15{
16    public int Level { get; }
17
18    public AdminUser(string name, int level) : base(name)
19    {
20        Level = level;
21        Console.WriteLine($"Admin level {Level}");
22    }
23}

If parent constructor work is heavy, make side effects explicit so object creation remains predictable.

Template Method Pattern for Safer Extension

A robust inheritance style avoids relying on child authors to remember base calls. The parent can expose a non-virtual workflow method that calls protected virtual hooks.

csharp
1using System;
2
3public abstract class JobRunner
4{
5    public void Execute()
6    {
7        Validate();
8        BeforeRun();
9        RunCore();
10        AfterRun();
11    }
12
13    protected virtual void BeforeRun() { }
14    protected virtual void AfterRun() { }
15    protected abstract void RunCore();
16
17    private void Validate()
18    {
19        Console.WriteLine("Base validation");
20    }
21}
22
23public class InvoiceJobRunner : JobRunner
24{
25    protected override void BeforeRun() => Console.WriteLine("Child pre-step");
26    protected override void RunCore() => Console.WriteLine("Child core run");
27    protected override void AfterRun() => Console.WriteLine("Child post-step");
28}

This pattern guarantees base invariants always execute.

override Versus new

A common mistake is method hiding with new when true polymorphic override was intended. Hidden methods do not participate in virtual dispatch through base references.

Use override unless you intentionally need hiding for compatibility reasons. If hiding is intentional, document it clearly because behavior can surprise maintainers.

Testing Parent-Child Contracts

Inheritance errors often appear as behavior drift rather than compile failures. Add tests for:

  • base validation is preserved
  • call order is correct
  • exceptions propagate as expected
  • side effects happen exactly once

These tests are especially important before refactoring class hierarchies.

Common Pitfalls

Forgetting to call base when base method enforces required validation breaks invariants silently.

Calling base in the wrong order can produce stale state or incomplete logging.

Using new instead of override causes confusing runtime behavior through parent references.

Putting hidden side effects in parent constructors makes child instantiation harder to reason about.

Summary

  • Use base to call parent behavior from child overrides and constructors.
  • Decide base-first or base-last based on invariant ownership.
  • Prefer template-method style when base steps must always run.
  • Avoid accidental method hiding when polymorphism is required.
  • Protect parent-child contracts with behavior-focused tests.

Course illustration
Course illustration

All Rights Reserved.