Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
ПЯВУ.docx
Скачиваний:
2
Добавлен:
23.04.2019
Размер:
210.36 Кб
Скачать

23.Методы и их наследование. Статические методы.

Наследование классовЕсли необходимо создать новый класс, лишь немного отличающийся от уже существующего, то нет необходимости в переписывании заново уже существующих полей и методов. В этом случае можно объявить, что новый класс является потомком или дочерним классом существующего класса, называемого предком или родительским классом. Все классы OP имеют единого общего родителя - класс TObject. Этот класс не имеет полей и свойств, но включает методы общего назначения, обеспечивающие весь жизненный цикл любых объектов - от их создания до уничтожения.

Новый класс наследует методы, поля, свойства своего родителя. В новом классе обычно добавляются новые методы, поля и свойства. В случае если новое поле или свойство имеет идентификатор, совпадающий с идентификатором поля или свойства в родительском классе, то соответствующий элемент родительского класса становится недоступным (перекрывается). Удалять объявленные в родительском классе поля, свойства и методы нельзя.

Наследование классов.

tуре

TParentClass=class

I:integer;

CounterValue: integer;

End;

TChildClass=Class(TParentClass)

CounterValue: Longint;

J: integer;

End;

Var

Parent: TParentClass;

Child: TChildClass;

В рассматриваемом примере объект Child будет иметь три поля:

1. I типа integer — унаследованное из класса TParentClass; 2. CounterValue типа Longint — новое поле, которое перекрыло поле CounterValue типа integer родительского класса;

3. J типа integer — новое поле, определенное в классе TChildClass.

Для методов при наследовании действуют те же правила, что и для полей классов, за исключением совпадения идентификаторов методов в классе-родителе и классе-потомке. В этих случаях для методов определены более сложные механизмы переопределения (перекрытие, перегрузка и др.). Выбор того или иного механизма определяется видом метода, который задается при его описании специальными директивами. К первому виду относятся статические методы, ко второму-виртуальные и динамические и, наконец, к третьему-перегружаемые методы. Модель наследования не поддерживает множественное наследование: каждый класс может иметь только один базовый класс. Частично реализовать множественное наследование можно с использованием интерфейсов.

Статические методы.Если при описании метода не задавались дополнительные директивы (по умолчанию), то метод является статическим. Если в классе-наследнике переопределить такой метод, то для объектов этого класса новый метод отменит родительский. Если обращаться к методу этого класса, то вызываться будет новый метод. Но если обратиться к объекту, как к объекту родительского класса, то вызываться будет метод родителя.

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

24.Перекрытие методов (полиморфизм) (override). Различие между виртуальными и динамическими методами.При определении метода в классе он может быть описан как виртуальный или динамический. Для этого после описания метода в родительском классе указывается специальная директива: соответственно virtual или dynamic. Если метод переопределяется в потомке, то для того, чтобы начал работать механизм полиморфизма после описания метода необходимо указать директиву override. Попытка перекрытия с директивой не override, а virtual или dynamic приведет не к перекрытию, а к созданию нового одноименного метода и полиморфизм не будет работать. Попытка применить директиву override при перекрытии статического метода вызовет ошибку компиляции.Если в каком-либо базовом типе метод был объявлен как виртуальный, то он остается виртуальным во всех классах-наследниках.

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

Теперь для этой иерархии можно написать некий алгоритм, который выполняет некоторое общее для всех объектов действие. В качестве конкретного объекта, выполняющего это действие нужно описать объект класса-родителя. Если теперь присвоить этому объекту какой-либо из его потомков, то алгоритм будет делать одно и то же, по сути, действие, но по-разному. Таким образом, один и тот же алгоритм сможет правильно обрабатывать разные виды объектов! Использование таких возможностей ООП может значительно упростить алгоритм программы в целом.

Различие между виртуальными и динамическими методамиВ случае динамических и виртуальных методов у компилятора нет возможности на этапе компиляции и компоновки жестко связать имя метода с адресом оперативной памяти, где находится его исполняемый код. Нужен механизм, позволяющий определить это прямо во время выполнения. Этот механизм называется поздним связыванием, он реализуется или через таблицу виртуальных методов или через таблицу динамических методов. В соответствии с этими механизмами есть два варианта реализации позднего связывания виртуальные и динамические методы. Синтаксис у обеих этих директив один тот же, результат — тоже. Различие заключается во внутреннем механизме, используемом компилятором для организации позднего связывания.

Виртуальные методы основаны на таблице виртуальных методов (VMT), которая представляет собой массив адресов всех виртуальных методов. Когда компилятор встречает обращение к виртуальному методу объекта, подставляет код, который обращается к (VMT) класса этого объекта и извлекает оттуда нужный адрес. Такая таблица заводится для каждого класса. В нем хранятся адреса всех виртуальных методов класса, независимо от того, были они перекрыты или нет в данном классе. В конечном счете, это приводит к эффекту распространения адресов таблицы виртуальных методов через всю иерархию классов. Отсюда вытекает достоинства и недостатки виртуальных методов: они вызываются сравнительно быстро, однако для хранения указателей на них в таблицах (VMT) требует большое количество памяти.

Вызовы динамических методов производятся при помощи уникально номера, определяющего метод. В таблице динамических методов класса хранят индексы и адреса только тех динамических методов, которые описаны в данном классе. При вызове динамического метода происходит поиск в этой таблице; в случае неудачи просматриваются таблицы DMT всех классов-предков в порядке иерархии и наконец, TObject, где имеется стандартный обработчик вызова динамических методов. Таким образом, поиск кода вызываемого метода в общем случае является более медленным, чем простой одношаговый вызов через VMT. Однако для больших и глубоких иерархий, использование динамических методов вместо виртуальных может привести к значительной экономии памяти.

Правила выбора между виртуальными и динамическими методами.

1. Если метод, скорее всего, будет перекрыт всеми потомками, его следует сделать виртуальным.

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

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

4. Следует учитывать, что самые быстрые и экономичные — статические методы, которые правда, не обеспечивают позднего связывания.