Полиморфизм и виртуальные методы



Введение в объектно-ориентированное программирование

Исторически сложилось так, что программирование возникло и развивалось как процедурное программирование, которое предполагает, что основой программы является алгоритм, процедура обработки данных.

Объектно-ориентированное программирование (ООП) — это методика разработки программ, в основе которой лежит понятие объект. Объект — это некоторая структура, соответствующая объекту реального мира, его поведению. Задача, решаемая с использованием методики ООП, описывается в терминах объектов и операций над ними, а программа при таком подходе представляет собой набор объектов и связей между ними.

Основные типы данных

К основным типам данных языка Delphi относятся: Т целые числа (integer); Т дробные числа (real); Т символы (char);

  • строки (string);
  • логический тип (boolean).

Целые числа и числа с плавающей точкой могут быть представлены в различных форматах (табл. П1.1 и П2.2).

Таблица П1.1.Целые числа

       
  Формат Диапазон  
  Shortint -128.. 127  
  Integer -32 768.. 32 767  
  Longint -2 147 483 648.. 2 147 483 647  
  Byte 0..255  
  Word 0..65535  
       

Таблица П1.2.Числа с плавающей точкой

         
  Формат Диапазон Кол-во значащих цифр  
  Real 2,9e-39.. 1,7e38 11-12  
  Single 1,5e-45.. 3,4e38 7-8  
  Double 5,0e-324.. 1,7e308 15-16  
  Extended 3,4e-4932.. 1,1e4932 19-20  

Стандартные функции и процедуры

При описании функций и процедур приняты следующие обозначения:

  • имена функций и процедур выделены полужирным;
  • формальные параметры изображены курсивом. В качестве параметра могут использоваться константы, переменные или выражения соответствующего типа. Если параметром обязательно должна быть переменная, то перед ним поставлено слово var. После параметра через двоеточие указывается его тип;
  • после списка параметров функций через двоеточие указан тип результата, возвращаемого функцией.

В табл. П1.3 приведены описания математических функций языка Delphi.

Таблица П1.3.Математические функции

       
  Функция Описание  
  Abs (Выражение) Абсолютное значение аргумента (целый или вещественный тип)  
  Sqr (Выражение) Квадрат аргумента (целый или вещественный тип)  
  Sqrt( Выражение: real) :real Квадратный корень аргумента  
  Sin (Выражение: real) : real Синус  
  Cos (Выражение: real) : real Косинус  
  Arctant Выражение: real) : real Арктангенс  
  Exp( Выражение: real) :real Экспонента  
  Ln ( Выражение : real ) : real Натуральный логарифм  
       

В табл. П1.4 приведены описания преобразований языка Delphi.

Таблица П1.4.Преобразования

       
  Преобразование Описание  
  Int( Выражение: real) :real Целая часть  
  Trunc (Выражение: real) : longint Целая часть  
  Round (Выражение: real) : longint Округление к ближайшему целому  
 

IntToStr (Выражение)

 

Преобразование числового выражения целого типа в строку

 
   
  FloatToStr (Выражение) Преобразование вещественного числа в его изображение  
  FloatToStrF ( Выражение, Формат, Точность, КоличествоЦифр) Преобразование вещественного числа в его изображение с возможностью выбора способа изображения  
  StrToInt ( Строка : string) Преобразование строки, изображающей целое или вещественное число, в число  
  StrToFloat ( Строка : string) Преобразование строки, изображающей вещественное число, в число  
       

В табл. 1.5 приведены описания функций работы со строками и символами.

Таблица П1.7.Работа со строками и символами

       
  Строковая функция Описание  
  Concat( Строка1: string, ... , Строкам: string) : string Copy ( Строка : string , НомерСимвола : integer, Длина: integer) : string Delete (var Строка :srting, НомерСимвола : integer, Сколько : integer) Length (Строка: string) : integer Pos (Строка: string, Подстрока: string) :byte Chr ( КодСимвола : byte ) Объединение нескольких строк в одну Выделение подстроки Удаление части строки Длина строки Позиция подстроки в строке Символ с указанным кодом  

 

 

Структура модуля

Модуль состоит из последовательности разделов. Каждый раздел начинается ключевым словом и продолжается до начала следующего раздела.

unit ИмяМодуля;

interface// раздел интерфейса

{ Здесь находятся описания процедур и функций модуля, которые могут использоваться другими модулями. )

const // раздел объявления констант

{ Здесь находятся объявления глобальных констант модуля, которые могут использоваться процедурами и функциями модуля.}

type // раздел объявления типов

{ Здесь находятся объявления глобальных типов модуля,

которые могут использоваться процедурами и функциями модуля }

var // раздел объявления переменных

{ Здесь находятся объявления глобальных переменных модуля, которые могут использоваться процедурами и функциями модуля }

implementation// раздел реализации

{ Здесь находятся описания (текст) процедур и функций модуля)

End.

Класс

Классический язык Pascal позволяет программисту определять свои собственные сложные типы данных — записи (records). Язык Delphi, поддерживая концепцию объектно-ориентированного программирования, дает возможность определять классы. Класс — это сложная структура, включающая, помимо описания данных, описание процедур и функций, которые могут быть выполнены над представителем класса — объектом.

Вот пример объявления простого класса:

TPerson = class

Private

fname: string[15]; faddress: string[35];

Public

procedureShow;

end;

Данные класса называются полями, процедуры и функции — методами.

В приведенном примере TPerson — это имя класса, fname и faddress - имена полей, show — имя метода.

Примечание

Согласно принятому в Delphi соглашению, имена полей должны начинаться с буквы f (от слова field — поле).

Описание класса помещают в программе в раздел описания типов (type).


Метод

Методы класса (процедуры и функции, объявление которых включено в описание класса) выполняют действия над объектами класса. Для того чтобы метод был выполнен, необходимо указать имя объекта и имя метода, отделив одно имя от другого точкой. Например, инструкция

professor. Show;

вызывает применение метода show к объекту professor. Фактически инструкция применения метода к объекту — это специфический способ записи инструкции вызова процедуры.

Методы класса определяются в программе точно так же, как и обычные процедуры и функции, за исключением того, что имя процедуры или функции, являющейся методом, состоит из двух частей: имени класса, к которому принадлежит метод, и имени метода. Имя класса от имени метода отделяется точкой.

Ниже приведен пример определения метода show класса TPerson

// метод Show класса TPerson procedureTPerson.Show;

Begin

ShowMessage( 'Имя:' + fname + #13+'Адрес:' + faddress );

end;

Примечание

В инструкциях метода доступ к полям объекта осуществляется без указания имени объекта.

 

 

Объект

Объекты как представители класса объявляются в программе в разделе var, например:

Var

student: TPerson; professor: TPerson;

Примечание

В Delphi объект — это динамическая структура. Переменная-объект содержит не данные, а ссылку на данные объекта. Поэтому программист должен позаботиться о выделении памяти для этих данных.

Выделение памяти осуществляется при помощи специального метода класса — конструктора, которому обычно присваивают имя Create (создать). Для того чтобы подчеркнуть особую роль и поведение конструктора, в описании класса вместо слова procedure используется слово constructor.

Ниже приведено описание класса TPerson, в состав которого введен конструктор:

TPerson = class private

fname: string [ 15 ];

faddress: string[35];

constructor Cireate; // конструктор

Public

procedure show; // метол

end;

Выделение памяти для данных объекта происходит путем присваивания значения результата применения метода-конструктора к типу (классу) объекта. Например, после выполнения инструкции

professor := TPerson.Create;

выделяется необходимая память для данных объекта professor.

Помимо выделения памяти, конструктор, как правило, решает задачу присваивания полям объекта начальных значений, т. е. осуществляет инициализацию объекта. Ниже приведен пример реализации конструктора для объекта TPerson:

constructorTPerson.Create;

Begin

fname := '';

faddress := '';

end;

Реализация конструктора несколько необычна. Во-первых, в теле конструктора нет привычных инструкций New, обеспечивающих выделение динамической памяти (всю необходимую работу по выделению памяти выполняет компилятор). Во-вторых, формально конструктор не возвращает значения, хотя в программе обращение к конструктору осуществляется как к методу-функции.

После объявления и инициализации объект можно использовать, например, установить значение поля объекта. Доступ к полю объекта осуществляется указанием имени объекта и имени поля, которые отделяются друг от друга точкой. Хотя объект является ссылкой, правило доступа к данным с помощью ссылки, согласно которому после имени переменной, являющейся ссылкой, надо ставить значок ^, на объекты не распространяется.

Например, для доступа к полю fname объекта professor вместо professor^.fname надо писать

professor.fname

Очевидно, что такой способ доступа к полям объекта более естественен.

Если в программе какой-либо объект больше не используется, то можно освободить память, занимаемую полями данного объекта. Для выполнения этого действия используют метод-деструктор Free. Например, для того, чтобы освободить память, занимаемую полями объекта professor, достаточно записать

professor.Free;

Полиморфизм и виртуальные методы

Полиморфизм — это возможность использовать одинаковые имена для методов, входящих в различные классы. Концепция полиморфизма обеспечивает з случае применения метода к объекту использование именно того метода, который соответствует классу объекта.

Пусть определены три класса, один из которых является базовым для двух других:

Tуре

// базовый класс TPerson = class

fname: string;// имя

constructorCreate(name:string);

function info: string;

virtual;

end;

// производный от TPerson TStud = class(TPerson)

fgr:integer; // номер учебной труппы

constructorCreate(name:string;gr:integer);

functioninfo: string; override; end;

// производный от TPerson TProf = class(TPerson)

fdep:string;// название кафедры

constructorCreate(name:string;dep:string);

function info: string;

override;

end;

В каждом из этих классов определен метод info. В базовом классе при помощи директивы virtual метод info объявлен виртуальным. Объявление метода виртуальным дает возможность дочернему классу произвести замену виртуального метода своим собственным. В каждом дочернем классе определен свой метод info, который замещает соответствующий метод родительского класса (метод порожденного класса, замещающий виртуальный метод родительского класса, помечается директивой override).

Ниже приведено определение метода info для каждого класса.

functionTPerson.info:string;

Begin

result := '';

end;

functionTStud.info:string;

Begin

result := fname + ' гp.' + IntTostr(fgr);

end;

functionTProf.info:string;

Begin

result := fname + ' каф.' + fdep;

end;

Так как оба класса порождены от одного и того же базового, объявить список студентов и преподавателей можно так (здесь следует вспомнить, что объект — это указатель):

list: array[1..SZL] of TPerson;

Объявить подобным образом список можно потому, что язык Delphi позволяет указателю на родительский класс присвоить значение указателя на дочерний класс. Поэтому элементами массива list могут быть как объекты класса TStud, так и объекты класса TProf.

Вывести список студентов и преподавателей можно применением метода info к элементам массива. Например, так:

st := '';

for i:=1 to SZL do // SZL - размер массива-списка

iflist[i] <> NIL

thenst := st + list[i].Info+#13; ShowMessage (st);

Во время работы программы каждый элемент массива может содержать как объект типа xstud, так и объект типа TProf. Концепция полиморфизма обеспечивает применение к объекту именно того метода, который соответствует типу объекта.

Следующая программа, используя рассмотренные выше объявления классов TPerson, TStud и TProf, формирует и выводит список студентов и преподавателей. Текст программы приведен в листинге 9.1.

 

 


Дата добавления: 2018-08-06; просмотров: 288; Мы поможем в написании вашей работы!

Поделиться с друзьями:






Мы поможем в написании ваших работ!