views:

95

answers:

3

Hi,

Consider the following code:

public class Vehicle
{
    public void StartEngine()
    {
        // Code here.
    }
}

public class CityBus : Vehicle
{
    public void MoveToLocation(Location location)
    {
        ////base.StartEngine();
        this.StartEngine();
        // Do other stuff to drive the bus to the new location.
    }
}

Is there any difference between this.StartEngine(); and base.StartEngine();, except that in the second case, StartEngine method cannot be moved to or overridden in CityBus class? Is there a performance impact?

+5  A: 

No difference, StartEngine() isn't virtual. You should not use base, in case you ever refactor it to make it virtual. The perf diff is not measurable.

Hans Passant
+3  A: 

The only difference is an explicit call to look at your parent class versus an implicit one that ends up in the same place through simple inheritance. Performance difference is negligible. like Hans Passant said, a call to base.StartEngine() will cause weird behavior if you make StartEngine virtual at some point.

You shouldn't need either qualifier to get the the right place. this.StartEngine() is almost always redundant when explicitly coded. You may have code that indirectly puts a this reference in a list of objects, but then it's the reference in the list being called:

public class Vehicle
{
    public void StartEngine()
    {
        // Code here.
    }

    //For demo only; a method like this should probably be static or external to the class
    public void GentlemenStartYourEngines(List<Vehicle> otherVehicles)
    {
       otherVehicles.Add(this);

       foreach(Vehicle v in Vehicles) v.StartEngine();
    }
}
KeithS
+2  A: 

There is absolutely no performance difference in this case.

As StartEngine is not virtual, the compiler, and later the jitter, know exactly what is meant by a call to it whether in the base, the derived class, or from an outside class.

If StartEngine were virtual, and the compiler and/or jitter can deduce that you are calling in respect to a CityBus rather than something derived from a CityBus, then what (very small) difference there is could also be removed as an optimisation.

If StartEngine were virtual, and the compiler and/or jitter cannot deduce whether you are calling in respect to a CityBus rather than a derived class, then the distinction between a base or direct call is vital for correctness.

As a rule, the only place to call a base method with base. is in an override of that method, to make use clearer. If the distinction between base and derived version is important elsewhere, then you should try to refactor so that base.SomeVirtualMethod() calls into base.SomeNonVirtual() which is hence always available even when derived.SomeVirtualMethod() changes the behaviour.

Jon Hanna