Полиморфизм на практике
В следующем примере класс Programmer дополняется двумя новыми членами (полем и свойством):
Public Class Programmer Inherits Employee Private m_gadget As String Public Sub New(ByVal theName As String. ByVal curSalary As Decimal) MyBase.New(theName .curSalary) End Sub Public Overloads Overrides Sub RaiseSalary(ByVal Percent As Decimal) MyBase.RaiseSalary(1.2D * Percent, "special") End Sub Public Property ComputerGadget() As String Get Return m_Gadget End Get SetCByVal Value As String) m_Badget = Val ue End Set End Property End Class
В процедуру Sub Main добавляются новые строчки:
Sub Main() Dim tom As New Employee("Tom". 50000) Dim sally As New Programmed"Sally". 150000) sally.ComputerGadget = "Ipaq" Dim ourEmployees.d) As Employee ourEmployees(0)= tom ourEmployees(l)= sally Dim anEmployee As Employee For Each anEmployee In ourEmployees anEmployee.RaiseSalary(0.1D) Console.WriteLine(anEmployee.TheName & "salary now is " & anEmployee.Salary()) Next Console.WriteLine(ourEmployeesd).TheName & "gadget is an "_ & ourEnployees(l).Gadget) Console. ReadLine() End Sub
При попытке откомпилировать новый вариант программы будет выдано сообщение об ошибке:
C:\book to comp\chapter 5\VirtualProblems\VirtualProblems\Modulel.vb(17): The name 'Gadget'is not a member of 'VirtualProblems.Employee.
Хотя объект sally, хранящийся в элементе массива ourEmployees(l), относится к типу Programmer, компилятор этого не знает и потому не может найти свойство ComputerGadget. Более того, при включенном режиме Option Strict (а отключать его не рекомендуется) для использования уникальных членов класса Programmer вам придется производить явное преобразование элементов массива к типу Programmer:
Console.WriteLine(ourEmployees(l).TheName & "gadget is an " & _ CType(ourEmployeesd), Programmer).ComputerGadget)
Преобразование объекта, хранящегося в объектной переменной базового типа, в объект производного класса называется понижающим преобразованием (down-casting); обратное преобразование называется повышающим (upcasting). Понижающее преобразование весьма широко распространено, однако использовать его не рекомендуется, поскольку при этом часто приходится проверять фактический тип объектной переменной в конструкциях следующего вида:
If TypeOf ourEmployees(l)Is Programmer Then Else If TypeOf ourEmployees(l)Is Employee Then End If
Перед вами те самые конструкции, для борьбы с которыми нам понадобился полиморфизм! (Повышающее преобразование всегда обходится без проблем, поскольку основополагающее правило наследования гласит, что объекты производных классов всегда могут использоваться вместо объектов базовых классов.)
Примечание
Хороший стиль программирования требует, чтобы при использовании специальных средств класса Programmer объекты хранились в контейнере, предназначенном только для типа Programmer. В этом случае вам не придется проверять возможность преобразования командой If-TypeOf.