Локальные процедуры и функции
⇐ ПредыдущаяСтр 7 из 7
Локальной функцией или процедурой называется подпрограмма, которая описана внутри другой подпрограммы. Рассмотрим пример:
procedure TForm1.Button1Click(Sender:TObject); Var X: Integer; { Локальная процедура } procedure Test; Begin Memo1.Lines.Add(¢Локальная процедура, X = ¢ + IntToStr(X)); end; Begin X:= 100; Memo1.Lines.Clear; Memo1.Lines.Add(¢Основная процедура, X = ¢ + IntToStr(X)); Test; end;
Обратите внимание на то, что описание процедуры Test находится в разделе объявления переменных метода Button1Click. Процедура Test называется локальной постольку поскольку ее описанием владеет другая процедура. Локальная процедура доступна только ее владельцу. Важным свойством локальных подпрограмм является то что им доступны любые переменные своего владельца. В нашем примере переменная X доступна как подпрограмме Button1Click, так и локальной процедуре Test. Если выполнить код, показанный выше, компонент Memo1 отобразит следующий текст:
Основная процедура, X = 100 Локальная процедура, X = 100
Перегрузка подпрограмм
Часто возникает необходимость выполнения одних и тех же действий над данными различных типов. Например, стандартная функция извлечения квадратного корня Sqrt возвращает значение, тип которого совпадает с типом аргумента целого или вещественного. Object Pascal, начиная с Delphi 4, предоставляет разработчикам объявлять одноименные функции и процедуры, принимающие аргументы различных типов. Это называется перегрузкой функций.
Новый термин. Перегрузка методов позволяет объявить две (и более) процедуры (или функции) с одинаковыми именами, но с различными списками параметров.
Выше мы рассмотрели пример программы с функцией Multiply, которая возвращает результат перемножения двух целых чисел. Допустим, что нам необходимо иметь также и функции, которые перемножают числа типа Double или Word.
Благодаря перегрузке, объявления соответствующих функций принимают вид:
function Multiply(Num1, Num2: Integer): Integer; overload; function Multiply(Num1, Num2: Double): Double; overload; function Multiply(Num1, Num2: Word): Word; overload;
Все функции имеют одно и то же имя (Multiply), но в их объявлении присутствует директива overload. Код реализации каждой из этих функций необходимо привести в секции implementation модуля, где они объявлены. При этом не надо обращать внимание на то, что эти функции выполняют одни и те же действия:
Implementation
function Multiply(Num1, Num2: Integer): Integer; overload; Begin Result:= Num1 * Num2; end;
function Multiply(Num1, Num2: Double): Double; overload Begin Result:= Num1 * Num2; end; function Multiply(Num1, Num2: Word): Word; overload; Begin Result:= Num1 * Num2; end;
При использовании любой из перегружаемых функций компилятор обеспечит вызов именно той из них, которой мы передадим параметры соответствующего типа. Например, в следующем фрагменте кода
Var X, Y, Z: Double; Begin X:= 1.5; Y:= 10.5; Z:= Multiply(X, Y); end;
будет вызвана та версия функции Multiply, которая «принимает» параметры типа Double.
ПРИМЕЧАНИЕ: В качестве критерия выбора нужной версии перегружаемой функции компилятор использует список ее фактических параметров. Перегружаемая функция обязательно должна иметь параметры. Так, следующие объявления не допускаются function DoSomething: Integer; overload; function DoSomething: Word; overload; В данной ситуации компилятор выдаст сообщение «Declaration of ¢DoSomething¢ differs from previous declaration».
Принцип перегрузки применим к процедурам, функциям и к методам объектов. Параметры по умолчанию
Любая процедура или функция может иметь параметры, значения которых заданы «по умолчанию». При вызове такой процедуры или функции соответствующие фактические параметры можно опустить. Рассмотрим пример подпрограммы с параметром по умолчанию:
// Объявление процедуры с параметром // EraseFirst, который по умолчанию имеет значение false. procedure Redraw(EraseFirst: Boolean = False); // описание процедуры procedure Redraw(EraseFirst: Boolean); Begin if (EraseFirst) then begin { код стирания изображения } end; { код рисования изображения } end;
Процедуру Redraw можно вызвать без фактического параметра. В такой ситуации на место отсутствующего фактического параметра компилятор подставит значение по умолчанию. Так, следующие строки кода по смыслу идентичны:
Redraw; Redraw(False);
При объявлении функций и подпрограмм обычные параметры должны предшествовать параметрам по умолчанию:
{ Объявление функции воспроизведения звукового файла} function PlayWaveFile(Name: string; Loop: Boolean = False; Loops: Integer = 10): Integer;
{ Вызовы попрограммы PlayWaveFile } R:= PlayWaveFile('chime.wav'); { не надо повторять звук } R:= PlayWaveFile('ding.wav', True); { проиграть 10 раз } R:= PlayWaveFile('bell.wave',True, 5); { проиграть 5 раз } Включение внешнего файла в модуль
Подключаемый файл – это обычный текстовый файл, содержимое которого необходимо «подставить» в нужное место модуля. Обычно в таких файлах размещают объявления констант, директивы компилятора или фрагменты кода, которые используются и в других модулях проекта. Иногда бывает удобно вынести в отдельный файл часть отлаженного кода, чтобы уменьшить объем текста, видимого в редакторе. Внешний файл автоматически включается в текст модуля при компиляции с помощью специальной директивы. Для имени подключаемого файла рекомендуется расширение .INC. Допустим, что внешний файл должен содержать код, показанный на листинге 2.2
Листинг2.2. Файл TEST.INC.
Const DefWidth = 500; DefHeight = 300; Type TCDRecord = record Number: integer; // Порядковый номер CD в коллекции Title: string; // Наименование Artist: string; // Исполнитель Year: integer; // Год выпуска Recorded: string; // Фирма-производитель Price: double; // Стоимость Market: string; // Где куплен end;
Чтобы создать включаемый файл, в главном меню Delphi надо выбрать File | New и затем дважды щелкнуть на пиктограмме Text диалога New Items. В результате откроется чистая страница редактора кода. Введите текст и сохраните файл под любым именем, выбрав в меню File | Save As.... Не забудьте при этом задать расширение имени INC, – иначе по умолчанию будет принято расширение TXT.
Чтобы включить внешний файл в текст модуля, необходимо воспользоваться директивой компилятора $I так как это показано в следующем примере:
unit Unit2; Interface Uses Windows, Messages, SysUtils, Classes,StdCtrls; {$I Test.inc} {... остальной текст модуля }
Директива $I дает указание компилятору взять исходный текст из файла TEST.INC и заменить им саму директиву. Можно считать, что действие директивы $I подобно копированию фрагмента текста из одного файла в буфер обмена и вставке содержимого буфера в результирующий файл. Необходимо следить чтобы включаемый файл был синтаксически корректным. В противном случае компилятор зафиксирует ошибку.
Воспользуйтесь поиском по сайту: ©2015 - 2024 megalektsii.ru Все авторские права принадлежат авторам лекционных материалов. Обратная связь с нами...
|