русс | укр

Мови програмуванняВідео уроки php mysqlПаскальСіАсемблерJavaMatlabPhpHtmlJavaScriptCSSC#DelphiТурбо Пролог

Компьютерные сетиСистемное программное обеспечениеИнформационные технологииПрограммирование


Linux Unix Алгоритмічні мови Архітектура мікроконтролерів Введення в розробку розподілених інформаційних систем Дискретна математика Інформаційне обслуговування користувачів Інформація та моделювання в управлінні виробництвом Комп'ютерна графіка Лекції


Деструктори


Дата додавання: 2014-04-22; переглядів: 1019.


Об’єкти, як інші типи даних, розміщені в динамічній пам’яті, можуть видалятися при потребі за допомогою процедури Dispose

 

Dispose(S);

 

Однак при видаленні непотрібного об’єкту може знадобитися дещо більше, ніж просте звільнення зайнятої ним динамічної пам’яті. Об’єкт може містити вказівники на динамічні структури чи об’єкти, які потрібно вивільнити чи очистити в певному порядку, особливо якщо використовується складна динамічна структура даних. Всі операції, необхідні для очистки динамічного об’єкту, повинні об’єднуватися в один метод таким чином, щоб об’єкт міг бути знищеним за допомогою одного виклику

Student.Done;

Метод Done повинен інкапсулювати всі деталі очистки свого об’єкту, а також всіх структур даних і вкладених об’єктів. Для позначення таких методів звичайно рекомендується використовувати ідентифікатор Done.

Часто корисно і допустимо визначати кілька методів очищення для даного типу об’єкту. Залежно від їх розміщення чи використання, чи залежно від стану і режиму на момент очищення складні об’єкти можуть вимагати очищення різними способами.

Pascal надає розробникам спеціальний тип методу, який називається деструктором, для очищення і видалення динамічних об’єктів. Деструктор об’єднує етап видалення об’єкту з іншими діями чи задачами, необхідними для даного типу об’єкту. Для одного типу об’єкту можна визначити кілька деструкторів.

type

TStudent=object

Name:String[30];

Date:string[10];

rate:real;

constructor init(nm,Dt:String;rt:real);

destructor done; virtual;

function GetName:string; virtual;

function getdate:string;

function getrate:real;

procedure showname;

procedure showdate;

procedure showrate;

end;

Деструктори можна успадковувати і вони можуть бути статичними чи віртуальними. Оскільки різні програми завершення об’єктів звичайно вимагають різних типів об’єктів, рекомендується завжди визначати деструктори віртуальними, щоб для кожного типу об’єктів виконувався правильний деструктор.

Нема необхідності вказувати зарезервоване слово DESTRUCTOR для кожного методу очистки, навіть якщо визначення типу об’єкту містить віртуальні методи. Насправді деструктори працюють лише з динамічними об’єктами. При очистці таких об’єктів деструктор виконує деякі спеціальні функції, гарантуючи, що в динамічній пам’яті буде вивільнятися правильне число байт. Але використання деструктора до статичних об’єктів теж не є помилкою і не призводить до некоректної роботи програми.

Основною перевагою використання деструктора є видалення з пам’яті поліморфних об’єктів, тобто тих, які були присвоєні екземпляру батьківського типу завдяки правилам сумісності. Будуючи код поліморфного об’єкта, компілятор під час компіляції точно не знає, який тип об’єкту насправді буде використаний. Єдине, що йому відомо – це ієрархія потомків предка певного типу, до якої цей об’єкт належить.

Очевидно, що розміри типів об’єктів відрізняються. Інформація про розмір об’єкта, який видаляється, стає доступною для деструктора в момент видалення завдяки вертанню до таблиці віртуальних методів екземплярів об’єктів певного типу VMT.

Для виконання звільнення пам’яті при пізньому зв’язуванні деструктор потрібно викликати як частину розширеного синтаксису процедури Dispose

Dispose(S,Done);

Деструктор об’єкту, на який вказує S, виконується як звичайний метод. Однак, як тільки остання дія буде виконана, деструктор почне шукати розмір екземпляра вказаного типу у VMT і передасть його розмір процедурі Dispose. Процедура Disposeзавершує процес шляхом видалення правильного числа байтів області динамічної пам’яті, яка відносилася до S^. Число звільнюваних байтів буде правильним незалежно від того, чи вказує S на екземпляр батьківського (TStudent) чи дочірнього (TStudent1) типу. Тому деструктор рекомендується робити віртуальним навіть якщо ніяких віртуальних методів об’єкт не містить.

Виклик деструктора поза процедурою Dispose не приведе до автоматичного вивільнення пам’яті.

Необхідно відмітити, що сам по собі метод деструктора може бути порожнім і виконувати лише функцію зв’язку з процедурою Dispose

 

Destructor TStudent.Done;

Begin

end;

 

оскільки основна інформація міститься не в тілі деструктора, а зв’язана з його заголовком, що містить слово Destructor

Деструктор дочірнього типу TStudent1 теж теж повинен останньою дією викликати відповідний деструктор свого безпосереднього предка, щоб звільнити поля всіх успадкованих вказівників об’єкту

 

Destructor TStudent1.Done;

Begin

Inherited Done;

end;


<== попередня лекція | наступна лекція ==>
Ключове слово INHERITED | Підсумок


Онлайн система числення Калькулятор онлайн звичайний Науковий калькулятор онлайн