Home > .NET Framework > Shadowing and Overriding

Shadowing and Overriding

Let us see some code first.

 
	/// 
	/// The class has to be declared abstract because it has an abstract method "AnAbstractMethod"
	/// Else there will be a compiler error
	/// 
	public abstract class Base
	{
		public Base()
		{			
		}

		public void ANonVirtualMethod()
		{
			Console.WriteLine("Base::ANonVirtualMethod");
		}

		public virtual void AVirtualMethod()
		{
			Console.WriteLine("Base::AVirtualMethod");
		}

		public virtual void AnotherVirtualMethod()
		{
			Console.WriteLine("Base::AnotherVirtualMethod");
		}

		public virtual void YetAnotherVirtualMethod()
		{
			Console.WriteLine("Base::YetAnotherVirtualMethod");
		}

		public abstract void AnAbstractMethod();
	}

	public class Derived : Base
	{
		public Derived()
		{			
		}

		/// 
		/// The following is not allowed as by default methods are virtual
		/// 
		////public override void ANonVirtualMethod()
		////{
		////	Console.WriteLine("Derived::ANonVirtualMethod");
		////}

		/// 
		/// If we remove the new the compiler flags a warning
		/// 
		public new void ANonVirtualMethod()
		{
			Console.WriteLine("Derived::ANonVirtualMethod");
		}

		public override void AVirtualMethod()
		{
			Console.WriteLine("Derived::AVirtualMethod");
		}

		public override void AnAbstractMethod()
		{
			Console.WriteLine("Derived::AnAbstractMethod");
		}

		/// 
		/// By default the overridden method is still virutal, 
		/// you can prevent this by specifying sealed along with override
		/// 
		public sealed override void AnotherVirtualMethod()
		{
			Console.WriteLine("Derived::AnotherVirtualMethod");
		}

		/// 
		/// This is taken to be new by default (shadows the base implementation)
		/// Compiler gives a warning too...
		/// 
		public void YetAnotherVirtualMethod()
		{
			Console.WriteLine("Derived::YetAnotherVirtualMethod");
		}
	}

	public class ShadowVsOverRideTestDriver
	{
		public static void Main(string[] args)
		{
			Base b ;
			Derived d = new Derived();
			b = new Derived();

			// Prints Base::ANonVirtualMethod
			b.ANonVirtualMethod();

			// Prints Derived::AVirtualMethod
			b.AVirtualMethod();

			// Prints Derived::AnotherVirtualMethod
			b.AnotherVirtualMethod();

			// Prints Base::YetAnotherVirtualMethod
			b.YetAnotherVirtualMethod();

			// Prints Derived::AnAbstractMethod
			b.AnAbstractMethod();

			// Prints Derived::ANonVirtualMethod (base method is shadowed)
			d.ANonVirtualMethod();

			// Prints Derived::AVirtualMethod
			d.AVirtualMethod();

			// Prints Derived::AnotherVirtualMethod
			d.AnotherVirtualMethod();

			// Prints Derived::YetAnotherVirtualMethod (base method is shadowed)
			d.YetAnotherVirtualMethod();

			// Prints Derived::AnAbstractMethod
			d.AnAbstractMethod();

			Console.ReadLine();
		}
	}

In C# by default all methods are non virtual. If you make a method as virtual then you need to specify it explicitly. This is done because unless and otherwise a method is designed, developed and tested for extensibility you should allow overriding of the method. Hence the choice has to be made explicitly by the class designer.

Another important concept is shadowing. If you have a method by name Copy in the derived class, this was not there in the version 1 of the Base class. Everything is fine. Now let us say the base class developer decides to add a method called copy in his base class. If by default we allow methods to be virtual in the base class and override in the derived class, The Copy will be overridden in the derived class. This may not have been the base class developer’s and the derived class developer’s instant. So the compiler emits a warning after which the derived class developer can decide whether it is a override of the base method or it shadows the base method.

More can be read here

Categories: .NET Framework
  1. Sudhir
    September 27, 2007 at 2:16 am

    good explanation

  1. No trackbacks yet.

Leave a comment