When we have new
in C#, that personally I see only as a workaround to override a property that does not have a virtual/overridable declaration, in VB.NET we have two "concepts" Shadows
and Overloads
.
In which case prefer one to another?
A derived type shadows the name of an inherited type member by redeclaring it. Shadowing a name does not remove the inherited type members with that name; it merely makes all of the inherited type members with that name unavailable in the derived class.
Shadowing redefines an entire method or function. Overriding redefines only the implementation of a method or function. Showing is used to protect against subsequent base class modification. Overriding does polymorphism by defining a different implementation. We can change the access modifier.
Method Overloading means defining multiple methods with the same name but with different parameters. Method Overriding. Method Overriding means override a base class method in the derived class by creating a method with the same name and parameters using virtual and override keywords.
Shadowing is the concept of using Polymorphism in Object Oriented Programming. When two programming elements share the same name, one of them can hide, or shadow, the other one.
I have actually confirmed by compiling the same code with Shadows
vs Overloads
for a method with an identical name and signature in the base class and looking at the output from ildasm
for both. The only difference is the Overloads
case specifies hidebysig
.
The significance of this is best explained by Jon Skeet in this answer.
But simply it means there is only a real difference if the base class has overloads of the method being redefined:
Shadows
will cause all of those overloads to be uncallable through the derived class, where as Overloads
only replaces the one method.Note that this is only a language construct and not enforced by the CLI (i.e. C# and VB.NET enforce this but other languages may not).
A simple code example:
Module Module1 Sub Main() Dim a1 As C1 = New C2 Dim a2 As New C2 a1.M1() a2.M1() a1.M2() a2.M2() a1.M3() a2.M3() a1.M1(1) ' Overloads on M1() allows the M1(int) to be inherited/called. a2.M1(1) a1.M2(1) ' Shadows on M2() does not allow M2(int) to be called. 'a2.M2(1) a1.M3(1) ' Shadows on M3() does not allow M3(int) to be called, even though it is Overridable. 'a2.M3(1) If Debugger.IsAttached Then _ Console.ReadLine() End Sub End Module Class C1 Public Sub M1() Console.WriteLine("C1.M1") End Sub Public Sub M1(ByVal i As Integer) Console.WriteLine("C1.M1(int)") End Sub Public Sub M2() Console.WriteLine("C1.M2") End Sub Public Sub M2(ByVal i As Integer) Console.WriteLine("C1.M2(int)") End Sub Public Overridable Sub M3() Console.WriteLine("C1.M3") End Sub Public Overridable Sub M3(ByVal i As Integer) Console.WriteLine("C1.M3(int)") End Sub End Class Class C2 Inherits C1 Public Overloads Sub M1() Console.WriteLine("C2.M1") End Sub Public Shadows Sub M2() Console.WriteLine("C2.M2") End Sub Public Shadows Sub M3() Console.WriteLine("C2.M3") End Sub ' At compile time the different errors below show the variation. ' (Note these errors are the same irrespective of the ordering of the C2 methods.) ' Error: 'Public Overrides Sub M1(i As Integer)' cannot override 'Public Sub M1(i As Integer)' because it is not declared 'Overridable'. 'Public Overrides Sub M1(ByVal i As Integer) ' Console.WriteLine("C2.M1(int)") 'End Sub ' Errors: sub 'M3' cannot be declared 'Overrides' because it does not override a sub in a base class. ' sub 'M3' must be declared 'Shadows' because another member with this name is declared 'Shadows'. 'Public Overrides Sub M3(ByVal i As Integer) ' Console.WriteLine("C2.M3(int)") 'End Sub End Class
The output of the above:
C1.M1 C2.M1 C1.M2 C2.M2 C1.M3 C2.M3 C1.M1(int) C1.M1(int) C1.M2(int) C1.M3(int)
The output shows the Shadows
calls are used when C2
is called directly and not when called indirectly through C1
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With