
Полиморфизм
Полиморфизм – это свойство родственных объектов (т.е. объектов, имеющих одного общего родителя) решать схожие по смыслу проблемы разными способами. Изменяя алгоритм того или иного метода в потомках объекта, программист может придавать этим потомкам отсутствующие у родителя специфические свойства. Для изменения метода необходимо перекрыть его в потомке, т.е. объявить в потомке одноименный метод и реализовать в нем нужные свойства. В результате в объекте-потомке и объекте-родителе будут действовать два одноименных метода, имеющих разную алгоритмическую основу и придающих объектам разные свойства.
Полиморфизм означает возможность определения единого по имени метода в каждом объектовом типе иерархической структуры разными способами.
Если несколько объектных типов связаны между собой отношениями родитель-потомок, то указателю на базовый тип может быть присвоено значение указателя на любой из дочерних типов.
Например. Пусть приведены три типа объектов и три переменные-указателя на эти типы:
Type
TPerson =Object
FName : string[25];
FAddress : string[25];
End;
TStud =object( TPerson)
FGroup : integer;
Procedure Print;
End;
TProf =object(TPerson)
FKaf : integer;
Procedure Print;
End;
Var Pperson: ^TPerson;
Pstud : ^TStud;
Pprof : ^TProf;
Для приведенного определения следующие инструкции присваивания являются верными:
Pperson:= Pstud;
Pperson:= Pprof;
Описанное свойство указателей на объектные типы позволяет организовать список студентов и преподавателей как массив указателей на объектный тип TPerson, например, так: Spisok : array[1..n] of ^TPerson;
Тогда инструкция For i:=1 to n do Spisok[i]^.print; выведет на экран список преподавателей и студентов. Элемент массива может быть указателем на TStud или на TProf. Поэтому нельзя заранее сказать какой из методов будет вызван – TStud.Print или TProf.Print Решение о выборе метода принимается во время выполнения программы.
Изложенный выше пример вывода студентов и преподавателей демонстрирует концепцию полиморфизма, которая состоит в том, что при применении метода к объекту используется именно тот метод, который соответствует типу объекта.
Ниже приведена программа, иллюстрирующая понятие «полиморфизм». Программа сначала формирует список, состоящий из объектов типа TStudent и Tprofessor, затем, применяя метод Print к элементам массива, выводит этот список на экран.
Program PolVir;
Const lenlist =10; {длина списка}
Type TPerson =Object
FName : string[30];
FAddress : string[40];
Procedure Init(Name, Address : string); {конструктор объекта}
Procedure Done; {деструктор объекта}
Procedure Print;
End;
TStudent =object( TPerson)
FGroup : integer;
Procedure Init(Name, Address : string; Group: integer);
Procedure Done; Procedure Print;
End;
TProfessor =object( TPerson)
FKafedra : string[30];
Procedure Init(Name, Address, Kafedra : string);
Procedure Done; Procedure Print;
End;
PStudent=^Tstudent;
PProf=^TProfessor;
Procedure TPerson.Init(Name, Address: string);
Begin
FName:=Name;
FAddress:= Address;
End;
Procedure TPerson.Done;
Begin
End;
Procedure TPerson.Print;
Begin
Writeln(FName);
Writeln(FAddress);
End;
Procedure TStudent.Init(Name, Address: string;Group:integer);
Begin
TPerson.Init(Name,Address);
FGroup:=Group;
End;
Procedure TStudent.Done;
Begin
End;
Procedure TStudent.Print;
Begin
TPerson.Print;
Writeln(‘гр. ’,FGroup);
End;
Procedure TProfessor.Init(Name, Address, Kafedra: string);
Begin
TPerson.Init(Name,Address);
FKafedra:=Kafedra;
End;
Procedure TProfessor.Done;
Begin
Inherited Done;
End;
Procedure TProfessor.Print;
Begin
TPerson.Print;
Writeln(‘каф. ’,Fkafedra);
End;
Var list : array[1..lenlist] of ^TPerson;
I: integer;
Begin {инициализация списка}
For i:=1 to lenlist do list[i]:=NIL;
{создать пять объектов и поместить в список}
List[1]:=new(PStudent,Init(‘Михаил Иванов’,’Лесной пр., д.29’,238);
List[2]:=new(PStudent,Init(‘Иван Жук’,’Весенняя ул., д.2, кв.17’,133);
List[3]:=new(PProf,Init(‘Игорь Манин’,’Некрасова ул., д.45, кв.8’,’ПОИТ’);
List[4]:=new(PProf, Init(‘Нина Непомнящая’,’Ромашковая ул., д.12,кв.10’,’ПОИТ’);
List[5]:=new(PStudent,Init(‘Кузьма Прутков’,’Долгобродская ул., д.2, корп.2, кв.17’,473);
{вывести объекты – элементы списка}
For i:=1 to lenlist do
If list[i] <> NIL then list[i]^.print;
{уничтожить объекты}
For i:=1 to lenlist do
If list[i] <> NIL then
Begin
Dispose(list[i],Done); {разрушение объекта}
List[i]:=Nil;
End;
Readln;
End.