Язык Clarion является языком "ориентированным на операторы". Такие языки исходят из того факта, что исходный код существует в виде ASCII файлов, каждая строка программы соответствует записи файла. Поэтому вместо знаков препинания можно воспользоваться разделителями записи (символами “возврат каретки” и “перевод строки”).
В общем, формат оператора в языке Clarion следующий:
метка ОПЕРАТОР[(параметры)] [,АТРИБУТ[(параметры)]] ...
Атрибуты задают характеристики элемента и используются только в операторах объявления данных. Исполняемые операторы имеют вид стандартного обращения к процедуре, за исключением операторов присваивания (A = B) и управляющих структур (таких как IF, CASE и LOOP).
Метка оператора должна начинаться в первой колонке строки исходного текста. Оператор без метки не может начинаться с первой колонки. Оператор заканчивается символом конца строки. Не помещающийся в строку оператор может быть продолжен на другой строке с помощью вертикальной
черты ( | ). Для размещения нескольких операторов на одной строке используется ; (точка с запятой).Будучи ориентированным на операторы, язык Clarion исключает многие из символов пунктуации, обязательных в других языках для идентификации меток и разделения операторов. Блок операторов начинается обозначением составного оператора и заканчивается оператором END (или точкой).
Смотри также:
Имена переменных и метки операторов, Структуры, Уточнение имени переменной, Зарезервированные слова, Специальные символы
Имена переменных и метки операторов
Операторы языка в исходном модуле можно разделить на две основные категории: операторы объявления данных и исполняемые операторы, или просто “данные” и “код”.
Операторы объявления данных резервируют области памяти, которыми при выполнении программы манипулируют исполняемые операторы. Указание метки обязательно для данных объявленных в программе. С помощью метки можно сослаться на любую переменную, структуру данных, процедуру и подпрограмму.
Метка указывает конкретное место в программе. Любой исполняемый оператор может идентифицироваться меткой. Это позволяет использовать в качестве точки перехода оператор GOTO. Даже если на нее нет ссылок, метка увеличивает на 10 байт размер исполняемого оператора.
Метка оператора PROCEDURE является именем процедуры. Использование метки оператора PROCEDURE в качестве исполняемого оператора вызывает выполнение этой процедуры. Метка оператора PROCEDURE используется в выражении или списке параметров другой процедуры для того, чтобы представить значение, возвращаемое процедурой.
Правила образования допустимых меток в Clarion:
Когда операторы объявления данных вложены в другие операторы объявления данных, то получаются составные структуры данных. В языке Clarion существует много составных структур данных: APPLICATION, WINDOW, REPORT, FILE, RECORD, GROUP, VIEW, QUEUE и т.д. Такие составные структуры должны заканчиваться точкой (.) или оператором END. Операторы IF, CASE, EXECUTE, LOOP, BEGIN и ACCEPT представляют собой исполняемые управляющие структуры. Они также должны заканчиваться точкой или оператором END (оператор LOOP может неявно заканчиваться операторами WHILE или UNTIL).
У переменных, объявленных внутри составных структур данных (GROUP, QUEUE, FILE, RECORD и т.д.) могут быть совпадающие имена, если только они не содержатся в одной и той же структуре. Для того чтобы точно указать поле, имеющее имя, которое совпадает с именем поля в другой структуре, и обеспечить уникальность имени, можно использовать атрибут PRE этой структуры, так как он описан в документации (Префикс:ИмяПеременной). Тем не менее, использование для этой цели атрибута PRE необязательно и его можно опустить.
К любой переменной в составной структуре данных можно обратиться, присоединяя к имени переменной спереди имя структуры через точку (ИмяСтруктуры.ИмяПременной). Такой способ уточнения имени следует использовать для любых полей в структурах, для которых не указан атрибут PRE. Для ссылок на переменные внутри любых структур, кроме структуры CLASS и поименованных переменных-указателей, вместо точки можно использовать двоеточие (:) (ИмяСтруктуры:ИмяПеременной) (это служит только для обеспечения совместимости с предыдущими версиями Clarion для Windows).
Для уточнения имени переменной, которая находится во вложенной составной структуре, следует спереди присоединить имя каждой структуры предыдущего уровня (если она имеет имя). Если же у какой-либо из вложенных структур отсутствует имя, то эта часть из уточнения имени опускается. Это похоже на анонимные структуры UNION в C++. Это означает, что в случае структуры GROUP (без атрибута PRE), в которой структура GROUP имеет имя, на отдельные поля записи нужно ссылаться таким образом: ВнешнееИмяГруппы.ВнутреннееИмяГруппы.ИмяПоля. Если внутренняя структура GROUP не имеет имени, ссылка на поля осуществляется так: ВнешнееИмяГруппы.ИмяПоля. Существует одно исключение из этого правила: метка структуры RECORD внутри FILE может быть опущена и поэтому, обращаться к полям внутри файла можно так: ИмяФайла.ИмяПоля вместо ИмяФайла.ИмяЗаписи.ИмяПоля.
Такой синтаксис уточнения имен используется также для ссылок на все элементы структур CLASS – и на элементы данных и методы. Для того чтобы обратиться к методу – элементу структуры CLASS, укажите НазваниеКласса.ИмяМетода в любом месте, где допустимо обращение к процедуре. Чтобы сослаться на элемент структуры GROUP, имеющей атрибут DIM, необходимо специфицировать номер элемента в массиве на уровне, где появляется атрибут DIM.
Пример:
MasterFile FILE,DRIVER('TopSpeed')
Record RECORD
AcctNumber LONG !Можно ссылаться как Masterfile.AcctNumber
END
END
Detail FILE,DRIVER('TopSpeed')
RECORD
AcctNumber LONG ! Можно ссылаться как Detail.AcctNumber
END
END
Memory GROUP,PRE(Mem)
Message STRING(30) ! Можно ссылаться как Mem:Message or Memory.Message
END
SaveQueue QUEUE
Field1 LONG ! Можно ссылаться как SaveQueue.Field1
Field2 STRING ! Можно ссылаться как SaveQueue.Field2
END
OuterGroup GROUP
Field1 LONG ! Можно ссылаться как OuterGroup.Field1
Field2 STRING ! Можно ссылаться как OuterGroup.Fie
ld2InnerGroup GROUP
Field1 LONG ! Можно ссылаться как OuterGroup.InnerGroup.Field1
Field2 STRING ! Можно ссылаться как OuterGroup.InnerGroup.Field2
END
END
OuterGroup GROUP,DIM(5)
Field1 LONG ! Можно ссылаться как OuterGroup[1].Field1
InnerGroup
GROUP,DIM(5) ! Можно ссылаться как OuterGroup[1].InnerGroupField1 LONG ! Можно ссылаться как OuterGroup[1].InnerGroup[1].Field1
END
END
Смотри также:
PRE, CLASS, Переменные-указатели
Приведенные ниже ключевые слова являются зарезервированными и не могут использоваться в качестве меток ни в каких случаях:
ACCEPT AND BEGIN BREAK
BY CASE CHOOSE COMPILE
CYCLE DO ELSE ELSIF
END EXECUTE EXIT FUNCTION
GOTO IF INCLUDE LOOP
MEMBER NEW NOT NULL
OF OMIT OR OROF
PARENT PROCEDURE PROGRAM RETURN
ROUTINE SECTION SELF THEN
TIMES TO UNTIL WHILE
XOR
Ключевые слова, приведенные ниже, могут использоваться в качестве меток структур данных или исполняемых операторов, но не могут быть метками операторов PROCEDURE. Их можно использовать в качестве имен параметров в прототипе, только если также указан тип данных параметра:
APPLICATION CLASS CODE DATA
DETAIL FILE FOOTER FORM
GROUP HEADER ITEM ITEMIZE
JOIN MAP MENU MENUBAR
MODULE OLECONTROL OPTION QUEUE
RECORD REPORT ROW SHEET
TAB TABLE TOOLBAR VIEW
WINDOW
Замечание: SELF и PARENT не могут использоваться в качестве имен переменных в любом классе или методе интерфейса.
Инициаторы:
! Восклицательным знаком начинается комментарий.
? Вопросительным знаком начинается метка соответствия полю, метка или, когда находится в первой колонке строки исходного текста, означает, что операторы, следующие за ним, выполняются только в режиме ОТЛАДКИ.
@ Знаком коммерческое “At” начинается шаблон.
* Звездочкой начинается имя параметра, передаваемого по адресу, в прототипе процедуры в структуре MAP.
~ Знак тильда впереди имени файла обозначает, что этот файл связывается в проект.
Терминаторы:
; Точка с запятой является разделителем исполняемых операторов.
CR/LF Комбинация символов “Возврат каретки”/“Перевод строки” также является разделителем исполняемых операторов.
. Точка завершает операторную структуру или структуру данных (заменитель оператора END).
| Вертикальная черта является символом продолжения оператора.
# Знак фунта в конце имени означает неявное объявление переменной типа LONG.
$ Знак доллара в конце имени означает неявное объявление переменной типа REAL.
" Двойные кавычки в конце имени означает неявное объявление переменной типа STRING.
Разделители:
( ) В круглые скобки заключается список параметров.
[ ] В квадратные скобки заключается список индексов массива.
' ' В одиночные кавычки заключается строковая константа.
{ } В фигурные скобки заключается коэффициент повторения символа в строковой константе, а также параметры свойства.
< > В угловые скобки заключается код ASCII символа в строковой константе или параметр в прототипе MAP, который может опускаться при обращении к процедуре.
: Двоеточие разделяет начало и конец “подстроки”
, Запятая разделяет параметры в списке.
Коннекторы:
. Десятичная точка в числовых константах или соединение имени составной структуры с именем одного из ее компонентов.
: Двоеточие соединяет префикс с меткой переменной.
$ Знак доллара соединяет метку структуры WINDOW или REPORT с меткой соответствия объекта в операторе присвоения значения свойству объекта.
Операции:
+ Символ плюс означает сложение.
- Символ минус означает вычитание.
* Звездочка обозначает умножение.
/ Слеш обозначает деление.
% Знак процента обозначает взятие остатка от деления.
^ Операция возведения в степень.
< Левая угловая скобка означает операцию “меньше”.
> Правая угловая скобка означает операцию “больше”.
= Знак равенства означает присвоение или равенство.
~ Тильда обозначает булеву операцию “логическое НЕ”.
& Амперсанд обозначает конкатенацию.
&= Амперсанд со знаком равенства обозначает назначение или равенство.
:=: Означает множественное присваивание.
PROGRAM
MAP
прототипы
[MODULE( )
прототипы
END ]
END
глобальные данные
CODE
операторы
[RETURN]
процедуры
PROGRAM
Обязательный первый оператор в программном исходном модуле.MAP
Обязательное объявление глобальных процедур.MODULE
Объявление исходных модулей.прототипы Объявление процедур.
Глобальные данные Объявляются глобальные данные, которые могут быть использованы всеми процедурами.
CODE
Заканчивают секцию объявления данных и начинает секцию исполняемых операторов.операторы Исполняемые операторы программы.
RETURN
Завершает выполнение программы. Возвращает управление операционной системе.процедуры
Исходные коды процедур в программном модуле.Оператор PROGRAM является первым обязательным оператором объявления в исходном модуле Clarion программы. Ему могут предшествовать только строки комментария. При компиляции имя файла, содержащего оператор PROGRAM, используется в качестве имен объектного (.OBJ) и исполняемого (.EXE) файлов. Оператор PROGRAM может иметь метку, но компилятором она игнорируется.
Программа, в состав которой входят процедуры, должна иметь структуру MAP. В ней объявляются прототипы процедур. Любая процедура, содержащаяся в отдельном исходном файле, должна быть объявлена в структуре внутри структуры MAP.
Данные, объявленные в программном модуле между ключевыми словами PROGRAM и CODE, являются глобальными статическими данными и могут быть доступны любой процедуре в программе.
Пример:
PROGRAM !Пример объявления программы
INCLUDE('EQUATES.CLW') !Включить стандартные метки соответствия
MAP
CalcTemp PROCEDURE !Прототип процедуры
END
CODE
CalcTemp !Обращение к процедуре
CalcTemp PROCEDURE
Fahrenheit REAL(0) !Объявление глобальных данных
Centigrade REAL(0)
Window WINDOW('Temperature Conversion'),CENTER,SYSTEM
STRING('Enter Fahrenheit Temperature: '),AT(34,50,101,10)
ENTRY(@N-04),AT(138,49,60,12),USE(Fahrenheit)
STRING('Centigrade Temperature:'),AT(34,71,80,10),LEFT
ENTRY(@N-04),AT(138,70,60,12),USE(Centigrade),SKIP
BUTTON('Another'),AT(34,92,32,16),USE(?Another)
BUTTON('Exit'),AT(138,92,32,16),USE(?Exit)
END
CODE !Начало раздела исполняемых операторов
OPEN(Window)
ACCEPT
CASE ACCEPTED()
OF ?Fahrenheit
Centigrade = (Fahrenheit - 32) / 1.8
DISPLAY(?Centigrade)
OF ?Another
Fahrenheit = 0
Centigrade = 0
DISPLAY
SELECT(?Fahrenheit)
OF ?Exit
BREAK
END
END
CLOSE(Window)
RETURN
Смотри также:
MAP, MODULE, PROCEDURE, Объявление данных и распределение памяти
MEMBER (идентифицировать дополнительный исходный файл)
MEMBER(
[ программа ] )[MAP
прототипы
END
][метка] локальные данные
процедуры
MEMBER
Первый обязательный оператор в модуле исходного текста, который не является программным исходным файлом.программа Текстовая константа, содержащая имя файла с исходной программой (без расширения). Если этот параметр опущен, то данный модуль является "универсальным модулем" который можно компилировать в любую программу, добавив его в проект.
MAP
Объявления локальных процедур. К объявленным здесь процедурам можно обращаться только из процедур данного MEMBER модуля.прототипы Объявления процедур.
локальные данные Объявляются локальные статические данные, на которые можно ссылаться только в процедурах, чей исходный текст содержится в данном MEMBER модуле.
процедуры Исходные тексты процедур в MEMBER модуле.
MEMBER
стоит первым оператором в исходом модуле, который не является программным исходным файлом. Ему могут предшествовать только строки комментариев. Он требуется в начале любого исходного файла, который содержит процедуры, используемые программой. Оператор MEMBER идентифицирует программу, к которой относится исходный модуль.MEMBER модуль может содержать локальную структуру MAP (которая может содержать структуры MODULE). Процедуры объявленные в этом MAP доступны для использования другими процедурами MEMBER модуля. Исходный текст процедур, объявленных в этом MEMBER MAP, может содержаться в исходном MEMBER модуле или другом файле (если он объявлен в структуре MODULE внутри MAP).
Если в MEMBER операторе опущен параметр программа, вы должны иметь структуру MAP, в которой содержатся объявления процедур. Вам также нужно ВКЛЮЧАТЬ любые стандартные EQUATE файлы, которые используются в вашем исходном тексте.
Если исходный текст процедур, объявленных в MEMBER модуле структуры MAP, содержится в отдельном файле, то их прототипы должны быть объявлены в структуре MODULE внутри структуры MAP. Исходный файл MEMBER модуля, содержащий описание процедур, должен также содержать собственную структуру MAP, которая объявляет те же самые прототипы тех же процедур
(то есть, прототипы должны быть, по крайней мере, в двух MAP структурах – в исходном модуле, содержащих их, и в исходном модуле, использующих их). Любая процедура, не объявленная в глобальной (программной) MAP структуре, должна быть объявлена в локальной(ых) структруре(ах) MAP MEMBER модуля, который содержит их исходный текст.Данные, объявленные в MEMBER модуле, между ключевыми словами MEMBER и PROCEDURE, являются статическими локальными модульными данными и могут быть доступны только процедурам данного модуля (если не переданы как параметр)
.Пример:
!Модуль Source1 содержит:
MEMBER
('OrderSys') !модуль входит в программу OrderSysMAP !объявление локальных процедур
Func1 PROCEDURE(STRING),STRING !Func1 известна только в этих двух модулях
MODULE('Source2.clw')
HistOrd2 PROCEDURE !HistOrd2 известна только в этих двух модулях
END
END
LocalData STRING(10) !Локальные данные по отношению к MEMBER модулю
HistOrd PROCEDURE !Объявление HistOrd процедуры
HistData STRING(10) !Объявление локальных данных к этой процедуре
CODE
LocalData = Func1(HistData)
Func1 PROCEDURE(RecField) !Объявление локальной процедуры
CODE
!Исполняемые операторы
! Модуль Source2 содержит:
MEMBER
('OrderSys') !Модуль относится к программе OrderSysMAP !Объявление локальных процедур
HistOrd2 PROCEDURE !HistOrd2 известна только в этих двух модулях
MODULE('Source1.clw')
Func1 PROCEDURE(STRING),STRING !Func1 известна только в этих двух модулях
END
END
LocalData STRING(10) !Объявление данных локальных к этому модулю MEMBER
HistOrd2 PROCEDURE !Объявление процедуры HistOrd2
CODE
LocalData = Func1(LocalData)
Смотри также:
MAP, MODULE, PROCEDURE, CLASS, Объявление данных и распределение памяти
MAP (объявить прототипы процедур)
MAP
прототипы
[MODULE( )
прототипы
END
]END
MAP
прототипы Объявляет процедуры.
MODULE
Объявляет member модуль исходного текста, который содержит определение прототипа в MODULE.Структура
MAP содержит прототипы, которые объявляют процедуры и внешние исходные модули, используемые в программном, MEMBER модуле или процедурах, которые не являются элементами структур CLASS.Структура MAP, находящаяся в программном модуле, объявляет прототипы процедур доступные в любом месте программы. Структура MAP в MEMBER модуле объявляет прототипы процедур, которые доступны в пределах данного MEMBER модуля. Те же прототипы могут быть размещены в нескольких MEMBER модулях, чтобы сделать их явно доступными для каждого модуля. Структура MAP также может быть включена в объявление процедуры. Все прототипы процедур, объявленных локально в структуре MAP процедуры, будут доступны только внутри данной процедуры.
Структура MAP обязательна для любой нетривиальной Clarion программы, потому что в нее компилятор автоматически вставляет модуль исходного текста BUILTINS.CLW. Этот файл содержит прототипы большинства процедур внутренней библиотеки Clarion, которые являются частью языка Clarion. Этот файл обязателен потому, что в самом компиляторе (для повышения эффективности) нет этих прототипов. Поскольку прототипы в файле BUILTINS.CLW используют те же самые метки соответствия констант, описанные в файле EQU
ATES.CLW, этот файл также автоматически включается компилятором в каждую программу Clarion.Пример:
!Один файл содержит:
PROGRAM !Пример программы в sample.cla
MAP
!Начало объявлений в MAPLoadIt PROCEDURE !Процедура LoadIt
END
!Конец map!В отдельном файле содержится:
MEMBER('Sample') !Объявление MEMBER модуля
MAP
!Начало объявлений в локальной структуре MAPComputeIt PROCEDURE !Прототип процедуры
END
!Конец MAPComputeIt Procedure
LOC:Var LONG
MAP
!Локальный mapProc1
END
Code
Proc1()
Return
Proc1 Procedure
Code
LOC:Var += 1
Return
Смотри также:
PROGRAM, MEMBER, MODULE, PROCEDURE, Прототипы процедур
MODULE (указать исходный файл member-модуля)
MODULE(
файл исходного текста)прототип
END
MODULE
Задает MEMBER модуль или внешнюю библиотеку.файл исходного текста
Строковая константа, которая содержит имя файла, содержащем исходный текст на языке Clarion, в котором объявлены процедуры. Если исходный файл представляет собой внешнюю библиотеку, то эта строка может содержать любой уникальный идентификатор.
прототип
Прототипы процедур, хранящихся в исходном файле.Структура MODULE именует MEMBER модуль, написанный на языке Clarion или внешнюю библиотеку, и содержит прототипы процедур, содержащихся в файле исходного текста. Структура MODULE может объявляться только внутри структуры MAP, и доступна для использования в любой структуре MAP, вне зависимости от того, где содержится структура MAP в программном или в MEMBER модуле.
Пример:
!Файл "sample.clw" содержит:
PROGRAM !Пример программы в sample.clw
MAP !Начало объявлений в структуре map
MODULE('Loadit')
!Исходный модуль loadit.clwLoadIt PROCEDURE !Процедура LoadIt
END
!Конец модуляMODULE('Compute')
!Исходный модуль compute.clwComputeIt PROCEDURE !Процедура ComputeIt
END
!Конец модуляEND !Конец map
!Файл "loadit.clw" содержит:
MEMBER('Sample') !Объявляет модуль MEMBER
MAP !Начало структуры map
MODULE('Process')
!Исходный модуль process.claProcessIt PROCEDURE !Процедура ProcessIt
END
!Конец модуляEND !Конец map
Смотри также:
MEMBER, MAP, Прототипы процедур
PROCEDURE (определить процедуру)
метка
PROCEDURE [ ( список параметров ) ]локальные данные
CODE
операторы
[RETURN( [
значение ] ) ]PROCEDURE
Начинает секцию исходного текста, который может быть выполнен в программе.метка Имя процедуры. При определении метода в структуре CLASS может содержать имя класса, присоединенное спереди к имени процедуры
.список параметров
Разделенный запятыми список имен (и, необязательно, их типы данных), значения которых передаются в процедуру. Эти имена определяют локальные ссылки на передаваемые параметры. При определении метода в структуре CLASS может содержать имя класса (называемый SELF) как неявный первый параметр (если имя класса не присоединено спереди к имени процедуры), и всегда должен содержать тип данных и имя параметра.локальные данные Объявляются локальные данные видимые только в этой процедуре.
CODE
Завершает секцию объявления данных и начинает секцию исполняемых операторов в процедуре.операторы Исполняемые операторы.
RETURN
Завершает выполнение процедуры. Возврат в точку, из которой было обращение к процедуре и возвращение значение выражения, в котором процедура использовалась (если это предполагалось).значение Числовая или строковая константа или переменная, которая специфицирует результат вызова процедуры.
PROCEDURE
начинает секцию исходного текста, который может быть выполнен из любой точки в программе. К ней обращаются, просто указав метку оператора PROCEDURE (и, если необходимо, со списком параметров) в качестве исполняемого оператора в программной секции программы или процедуры.В списке параметров следом за именем (обязательным), под которым параметр используется внутри данной процедуры, возможно (но не обязательно) определяется тип данных параметра. Параметры разделяются запятой. Если процедура перегружаемая (имеет несколько определений), то наряду с меткой обязателен и тип данных каждого параметра (включая заключенные в угловые скобки, означающее возможность опускания параметра). Список параметров может быть точно таким же, как в прототипе процедуры, если прототип содержит метки параметров.
Процедура может содержать одну или несколько подпрограмм среди исполняемых операторов. Подпрограмма – секция исполняемого кода локальная по отношению к процедуре, которая вызывается оператором DO.
При выполнении оператора RETURN, процедура заканчивается и возвращает управление в точку вызова. После последнего выполняемого оператора в процедуре, в конце исходного текста, при появлении первого оператора ROUTINE или PROCEDURE, происходит неявное выполнение оператора RETURN.
Если процедура должна возвращать значение, оператор RETURN обязателен. Имя такой процедуры может использоваться в выражениях или передаваться как параметр в другую процедуру. Ее также можно вызвать как процедуру, не возвращающую значение, если логика программы не требует возврата значения. В этом случае, если прототип процедуры не имеет атрибута PROC, компилятор сгенерирует предупреждение, которое можно без опасения проигнорировать.
Данные, объявленные в процедуре между ключевыми словами PROCEDURE и CODE являются локальными для процедуры и доступны только этой процедуре (за исключением передачи их в качестве параметров в другую процедуру). Эти данные располагаются в памяти в момент входа в процедуру и освобождаются по ее завершении. Если объем данных меньше порогового для стека значения (по умолчанию 5K), то они помещаются в стек. В противном случае, память выделяется из “кучи”.
Процедура должна иметь прототип, объявленный в структуре CLASS или MAP программного или MEMBER модуля. В случае указания прототипа процедуры в программной структуре MAP, обращение к ней возможно из любых других процедур данной программы. Если же процедура представлена прототипом в MEMBER модуле, то обращение к ней возможно только из процедур этого MEMBER модуля.
Пример:
PROGRAM !Пример программы
MAP
OpenFile PROCEDURE
(FILE AnyFile)!Прототип процедуры с параметрамиShoTime PROCEDURE
!Прототип процедуры без параметровDayString PROCEDURE
,STRING !Прототип процедуры, которая возвращает значениеEND
FileOne FILE,DRIVER('Clarion') !Объявление файла
RECORD !начало объявления структуры Record
Name STRING(20)
Number LONG
END !Конец объявления структуры Record
END !Конец объявления файла
TodayString STRING
TodayString = DayString()!Вызывается процедура с возвращением значения
OpenFile(FileOne) !Вызов процедуры открытия файла
ShoTime !Вызов процедуры ShoTime
!Исполняемые операторы
OpenFile PROCEDURE
(FILE AnyFile)!Открывает некий файлCODE !Начало секции исполняемых операторов
OPEN(AnyFile) !Открытие файла
IF ERRORCODE() = 2 !Если файл не найден
CREATE(AnyFile) !создать его
END
RETURN !Возврат в точку вызова
ShoTime PROCEDURE
!Показать времяTime LONG !Локальная переменная
Window WINDOW,CENTER
STRING(@T3),USE(Time),AT(34,70)
BUTTON('Exit'),AT(138,92),USE(?Exit)
END
CODE !Начало секции исполняемых операторов
Time = CLOCK() !Получить системное время
OPEN(Window)
ACCEPT
CASE ACCEPTED()
OF ?Exit
BREAK
END
END
RETURN !Возврат в точку вызова
DayString PROCEDURE
!Процедура DayStringReturnString STRING(9),AUTO !Инициализация локальной переменной
CODE !Начало секции исполняемых операторов
EXECUTE (TODAY() % 7) + 1 !Определение дня недели по системной дате
ReturnString = 'Sunday'
ReturnString = 'Monday'
ReturnString = 'Tuesday'
ReturnString = 'Wednesday'
ReturnString = 'Thursday'
ReturnString = 'Friday'
ReturnString = 'Saturday'
END
RETURN(ReturnString) !Возврат результата
Смотри также:
Прототипы процедур, Объявление данных и распределение памяти, Перегрузка процедур, CLASS, ROUTINE, MAP
CODE (начало исполняемых операторов)
CODE
Оператор
CODE отделяет в программном модуле, процедуре или подпрограмме секцию объявления данных от секции исполняемых операторов (программной секции). За оператором CODE следует первый исполняемый оператор в программном модуле, процедуре или подпрограмме. Слово "Code" является зарезервированным словом и не может использоваться в качестве метки переменной или процедуры.Пример
:PROGRAM
!Здесь объявляются глобальные данные
CODE
!Здесь находятся исполняемые операторы
OrdList PROCEDURE !объявление процедуры
!Здесь объявляются локальные данные
CODE
!начало секции исполняемых операторов!Здесь находятся исполняемые операторы
Смотри также:
PROGRAM, PROCEDURE
DATA (начать локальную секцию данных подпрограммы)
DATA
Оператор
DATA начинает секцию описания локальных данных в подпрограмме. Любая подпрограмма, содержащая секцию DATA, должна также содержать оператор CODE, чтобы завершить секцию описания данных. Переменные, объявленные в разделе данных подпрограммы, не могут иметь атрибутов STATIC или THREAD.Пример:
SomeProc PROCEDURE
CODE
!операторы кода
DO Tally !Вызов подпрограммы
!операторы
Tally ROUTINE !Начало подпрограммы, конец программной секции
DATA
CountVar BYTE !Объявление локальной переменной
CODE
CountVar +
= 1 !Увеличивающий счетчикDO CountItAgain !Вызов другой подпрограммы
EXIT !и выход из подпрограммы
Смотри также:
CODE, ROUTINE
ROUTINE (объявить локальную подпрограмму)
метка
ROUTINE[ DATA
локальные данные
CODE ]
операторы
ROUTINE Объявляет начало локальной подпрограммы.
метка Имя подпрограммы. Не должна дублировать имя любой процедуры.
DATA
Начало операторов объявления данных.локальные данные Объявляет локальные данные видимые только в этой подпрограмме.
CODE
Начало исполняемых операторов.операторы Исполняемые операторы программы.
Оператор
ROUTINE объявляет начало локальной подпрограммы. Она локальна по отношению к процедуре, в которой написана, и должна находиться в конце ее программной секции. Все переменные, доступные в процедуре доступны локальной подпрограмме, включая данные локальные для процедуры, для модуля и глобальные данные.Подпрограмма может содержать свои собственные локальные данные, ограниченные самой подпрограммой, в которой они описаны. Если в подпрограмме имеется описание локальных данных, то ему должен предшествовать оператор DATA, а после описания - оператор CODE. Так как подпрограмма ROUTINE имеет собственную область имен, метки переменных могут дублировать имена переменных используемых в других подпрограммах или даже процедуре, содержащей подпрограмму.
Обращение к локальной подпрограмме производится оператором DO, за которым следует метка локальной подпрограммы. После выполнения локальной подпрограммы, управление передается оператору, следующему за оператором DO. Локальная подпрограмма заканчивается с концом исходного файла или с началом другой подпрограммой или процедурой. Для того, чтобы завершить выполнение локальной подпрограммы, может использоваться оператор EXIT (подобно оператору RETURN в процедуре).
Использование подпрограмм имеет некоторые вопросы, связанные с эффективностью, что не очевидно:
Пример:
SomeProc PROCEDURE
CODE
!Операторы
DO Tally !Вызов подпрограммы
!некие исполняемые операторы
Tally ROUTINE
!Начало подпрограммы, конец процедурыDATA
CountVar BYTE !Объявление локальной переменной
CODE
CountVar += 1 !Нарастающий счетчик
DO CountItAgain !Вызов другой подпрограммы
EXIT !и выход из подпрограммы
Смотри также
: PROCEDURE, EXIT, DO, DATA, CODE
END
Оператор
END заканчивает объявление структуры данных или составной исполняемый оператор. Функционально эквивалентен точке (.).Принято оператор END выравнивать на ту же колонку, в которой начинается завершаемая им структура, а операторы структуры пишутся с отступом для улучшения читаемости. Обычно, оператор END используется для завершения структур состоящих из нескольких строк, тогда как точка - для структур, занимающих одну строку. Если имеются вложенные исполняемые структуры, и все они заканчиваются в одном месте, то вместо нескольких операторов END на нескольких
строках используются несколько точек на одной строке.Пример:
Customer FILE,DRIVER('Clarion') !Объявление файла
RECORD !Объявление структуры record
Name STRING(20)
Number LONG
END !Конец структуры record
END !Конец объявления файла
Archive FILE,DRIVER('
Clarion') !Объявление файлаRECORD !Объявление структуры record
Name STRING(20)
Number LONG
END END !Заканчивает структуру record и файла
CODE
IF Number <> SavNumber !Начало структуры IF
DO GetNumber
END !Конец структуры IF
IF SomeCondition THEN BREAK END !Заканчивается оператором END
CASE Action !Начало структуры case
OF 1
DO AddRec
IF Number <> SavNumber !Начало структуры IF
DO SomeRoutine
END !Конец структуры IF
OF 2
DO ChgRec
OF 3
DO DelRec
END
!Конец структуры case
Последовательность выполнения операторов
В секции CODE программы на Clarion операторы обычно выполняются по одному, в последовательности их расположения в исходном тексте. Для того чтобы изменить последовательность выполнения операторов, используются управляющие операторы и обращения к процедурам.
Обращение к процедуре изменяет последовательность выполнения программы путем перехода к вызываемой процедуре и выполнения содержащихся в ней исполняемых операторов. Когда в вызванной процедуре выполняется оператор RETURN или в ней выполнен последний оператор, управление возвращается оператору, следующему за обращением к процедуре, возвращая значение (если это предусмотрено в процедуре).
Управляющие структуры IF, CASE, LOOP, ACCEPT и EXECUTE изменяют последовательность выполнения, основываясь на вычислениях выражений. Когда значение выражения вычислено, управляющая структура, в зависимости от условий, выполняет содержащиеся в ней операторы. ACCEPT это тоже loop-тип (цикличный тип), но он не оценивает выражений.
Кроме того, ветвление происходит при выполнении операторов GOTO, DO, CYCLE, BREAK, EXIT и RETURN. Выполнение этих операторов немедленно и безусловно изменяет нормальную последовательность выполнения программы.
Процедура START начинает новый процесс выполнения, безусловно переключая выполнение на этот процесс. Однако, щелкнув мышкой в активном окне другого процесса, пользователь может активировать выполнение этого другого процесса.
Пример:
PROGRAM
MAP
ComputeTime PROCEDURE(*GROUP) !
Matc
hMaster PROCEDURE !Передача группы в качестве параметраEND
ParmGroup GROUP
!Объявление группыFieldOne STRING(10)
FieldTwo LONG
END
CODE !Начало исполняемых операторов
FieldTwo = CLOCK() !Выполнить сперва
ComputeTime(ParmGroup) !Выполнить затем, передав управление в процедуру
MatchMaster !Выполнить после того, как выполнится процедура
Обращение к процедурам
ИмяПроцедуры
[(параметры)]ВозвращаемаяПеременная = ИмяФункции
[(параметры)]ИмяПроцедуры
Имя процедуры, как оно объявлено в прототипе процедуры.параметры Необязательный список параметров, передаваемых процедуре. Список параметров может представлять собой одну или несколько переменных или выражений. Параметры разделяются запятыми и объявляются в прототипе.
ВозвращаемаяПеременная
Имя переменной, в которую заносится возвращаемое процедурой значение.
ИмяФункции Имя процедуры, возвращающей значение, как оно объявлено в прототипе процедуры.
Процедура вызывается указанием ее имени (с возможным списком параметров) в качестве оператора в секции CODE программы или процедуры. Список параметров должен соответствовать списку, объявленному в прототипе процедуры. К процедуре нельзя обращаться в выражении.
Процедура, которая возвращает значение, вызывается указанием ее имени (с возможным списком параметров) в качестве компонента выражения или в списке параметров, передаваемых в другую процедуру. Список параметров должен соответствовать списку, объявленному в прототипе процедуры. Кроме того, если возвращаемое процедурой значение не играет роли, то к ней можно обратиться указанием ее имени (с возможным списком параметров) таким же образом, как к процедуре, которая не возвращает значение, если это не является необходимым. На такое использование процедуры компилятор выдаст предупреждение, которое можно безболезненно проигнорировать (за исключением случая, когда в прототипе размещен атрибут PROC).
Если процедура является методом какого-либо класса, то ИмяПроцедуры должно начинаться с имени объекта класса, за которым через точку следует имя процедуры (имяобъекта.ИмяПроцедуры).
Пример:
PROGRAM
MAP
ComputeTime PROCEDURE(*GROUP) !Передача группы в качестве параметра
MatchMaster PROCEDURE,BYTE,PROC !Процедура возвращает значение и ей не передается
! параметров
END
ParmGroup GROUP !Объявление группы
FieldOne STRING(10)
FieldTwo LONG
END
CODE
FieldTwo = CLOCK() !Встроенная процедура вызывается как выражение
ComputeTime(ParmGroup) !Вызов процедуры ComputeTime
MatchMaster() !Обращение к функции как процедуре
Смотри также:
PROCEDURE
имя
PROCEDURE [(список параметров)] [,типы возвращаемых значений] [,соглашение о передаче параметров] [,RAW] [,NAME( )] [,TYPE][,DLL( )] [,PROC] [,PRIVATE] [,VIRTUAL] [,PROTECTED] [,REPLACE] [,DERIVED]
имя
Метка оператора PROCEDURE, которая определяет начало секции исполняемых операторов.PROCEDURE
Необходимое ключевое слово.список параметров Типы данных параметров. За типом данных каждого параметра может следовать метка, использованная для документирования параметра (и только). Каждый параметр может включать присвоение значения, используемого по умолчанию (константы) которое передается, если параметр опущен.
типы возвращаемых значений
Тип возвращаемого процедурой значения.
соглашение о передаче параметров
Задает соглашение о передаче параметров через стек по типу языка C или PASCAL.
RAW
Указывает, что для параметров типа STRING или GROUP передается только их адрес в памяти (без длины передаваемой строки). Кроме того, этот атрибут изменяет поведение параметров со знаками ? и *? спереди. Этот атрибут служит только для совместимости с функциями на языках 3-го поколения и не действует для процедур, написанных на языке Clarion.NAME
Задает альтернативное, “внешнее” имя процедуры.TYPE
Указывает, что прототип является определением типа процедуры, передаваемой в качестве параметра.DLL
Указывает, что данная процедура находится во внешней библиотеке DLL.PROC
Задает, что обращение к процедуре, возвращающей значение, как к процедуре, не возвращающей значение, не вызывает предупреждающего сообщения компилятора.PRIVATE
Указывает, что к данной процедуре можно обращаться из других процедур, расположенных в том же самом программном модуле (обычно используется в классах).VIRTUAL
Указывает, что данная процедура представляет собой виртуальный метод структуры CLASS.PROTECTED
Указывает, что PROCEDURE может быть вызвана только из другой процедуры того же объекта CLASS или любого другого CLASS, напрямую полученного из текущего.REPLACE
Указывает, что процедуры "Construct" или "Destruct" в полученном объекте CLASS полностью заменяет конструктор или деструктор родительского класса.DERIVED
Указывает, что PROCEDURE является производным методом структуры CLASS, прототип которой должен совпадать с прототипом родительского класса.Все процедуры в программе должны быть представлены прототипами в структуре MAP или CLASS. Прототип точно говорит компилятору, какую форму обращения к процедуре ожидать среди исполняемых операторов.
На предыдущей странице перечислены две допустимые формы объявления прототипов. Первая, использующая ключевое слово PROCEDURE, допустима для использования в любом месте и является предпочтительной. Вторая форма пока поддерживается только для совместимости с предыдущими версиями Clarion.
Прототип состоит из:
Дополнительно можно указать для процедуры соглашение о передаче параметров через стек по типу языка C (справа налево) или PASCAL (слева направо и совместимыми с Windows 32-bit). Этим обеспечивается совместимость с библиотеками третьих фирм, написанными на других языках (если они не были компилированы Topspeed компилятором). Если соглашение о передаче параметров не указано, то по умолчанию используется передача параметров в регистрах, принятая в языках семейства TopSpeed.
Независимо от того, передаются ли параметры-значения или параметры-переменные, атрибут RAW позволяет передать просто адрес памяти (*?) для STRING или GROUP в процедуру или функцию не на языке Clarion. Обычно для STRING и GROUP передаются адрес и длина строки или группы. Указание атрибута RAW исключает передачу длины. Это наиболее полезно при использовании внешних библиотечных функций, которые принимают только адрес строки.
Атрибут NAME обеспечивает процедуре внешнее, альтернативное имя. Это также делается для обеспечения совместимости с написанными на других языках библиотеками третьих фирм. Например, в некоторых компиляторах языка С, наряду с принятым в С порядком передачи параметров для функций через
стек, компилятор добавляет спереди к имени функции символ подчеркивания. Указание атрибута NAME позволяет компоновщику корректно разрешить ссылку на имя функции.Атрибут TYPE означает, что прототип не указывает на какую-либо конкретную процедуру. Вместо этого он указывает имя прототипа, использованное в другом прототипе, чтобы обозначить тип процедуры, передаваемый в другую процедуру в качестве параметра.
Атрибут DLL указывает, что данная процедура размещается в библиотеке DLL. Для 32-битовых приложений атрибут DLL обязателен, так как такие библиотеки являются настраиваемыми (перемещаемыми) в 32-битовом адресном пространстве, что требует от компилятора еще одного дополнительного разыменовывания (преобразования адреса) при обращении к процедуре.
Атрибут PRIVATE задает, что к данной процедуре могут обращаться только процедуры, расположенные в этом же самом модуле. Этот атрибут чаще всего используется в MAP-структуре модуля, хотя может использоваться и в глобальной структуре MAP.
Когда имя прототипа указывается в списке параметров другого прототипа, это означает, что прототипируемая процедура будет принимать метку процедуры, которая принимает точно такие же параметры ( и имеет точно такой же тип возвращаемого значения, если она возвращает значение). Прототип с атрибутом TYPE не может иметь атрибута NAME.
Пример:
MAP
MODULE('Test') !'test.clw' содержит эти процедуры и функции
MyProc1 PROCEDURE
(LONG) ! параметр-значение типа LONGMyProc2 PROCEDURE
(<*LONG>) ! возможно отсутствие параметраMyProc3 PROCEDURE(LONG=23
) ! Если параметр опущен, то передается 23END
MODULE('Party3.Obj') ! Библиотека третьей фирмы
Func46 PROCEDURE
(*CSTRING),REAL,C,RAW ! передается только адрес строки CSTRING в функцию на CFunc47 PROCEDURE
(*CSTRING),*CSTRING,C,RAW ! возвращает указатель на CSTRINGFunc48 PROCEDURE
(REAL),REAL,PASCAL ! соглашение о вызове как в PASCALFunc49 PROCEDURE
(SREAL),REAL,C,NAME('_func49') ! соглашение о вызове как в C и внешнее! имя
END
MODULE('STDFuncs.DLL') ! DLL-библиотека стандартных функций
Func50 PROCEDURE(SREAL),REAL,PASCAL,DLL
END
END
Смотри также:
MAP, MEMBER, MODULE, NAME, PROCEDURE, RETURN, Списки параметров в прототипах, Перегрузка процедур, CLASS
Списки параметров в прототипах – основной синтаксис
[CONST]
тип [ метка ]<[CONST]
тип [ метка ] >тип
[ метка ] = по умолчаниюCONST
Необязательный классификатор для параметра, который допустим только для параметра-переменной. Это означает, что параметр, переданный по адресу, не может быть изменен в процедуре и будет интерпретироваться как константа.тип Тип данных параметра. Это может быть параметр-значение, параметр-переменная, неуказанный тип данных, параметр-процедура или именованные объекты GROUP, QUEUE, или CLASS.
метка Необязательная документальная метка параметра. Эта метка необязательна и помещается в прототипе только для документальных нужд.
< >
Скобки-уголки указывают на то, что параметр может быть пропущен. Процедура OMITTED определяет такую установку. Все типы параметра могут быть пропущены.= по умолчанию Значение по умолчанию показывает, что численный параметр может быть пропущен и если это так, то используется значение по умолчанию. Процедура OMITTED не определит упущения, так как присутствует значение по умолчанию. Действительно только в простых численных типах.
Список параметров представляет собой разделенный запятыми список типов данных, передаваемых в процедуру. Весь список параметров, заключенный в скобки, следует за ключевым словом PROCEDURE (или именем). За любым типом данных через пробел может следовать соответствующая синтаксису языка метка параметра (которая игнорируется компилятором и служит только для документирования параметра). Определение любого числового параметра (передаваемого “по значению”) может, кроме того, содержать присвоение числовой константы обозначению типа данных или метке параметра, если таковая имеется. Этим определяется значение по умолчанию, передаваемое в том случае, когда данный параметр опущен.
Если значение, передаваемое по умолчанию не определено, то параметр, который может опускаться при обращении к процедуре, в списке параметров в прототипе должен быть заключен в угловые скобки (<>). Определить во время выполнения программы факт опускания параметра можно с помощью функции OMITTED (за исключением тех опущенных параметров, для которых определено значение, передаваемое по умолчанию
).Пример:
MAP
MODULE('Test')
MyProc1 PROCEDURE(LONG) !
параметр - значение LONGMyProc2 PROCEDURE(<LONG>
) ! OMIT- параметр - LONGMyProc3 PROCEDURE(LONG=23
) ! передается 23 , если параметр опущенMyProc4 PROCEDURE(LONG Count, REAL Sum
) ! LONG передает Count и REAL передает SumMyProc5 PROCEDURE(LONG Count=1,REAL Sum=0
)! Count по умолчанию - 1, Sum - 0END
END
Параметры-значения
Параметры-значения являются “передаваемыми по значению”. В “вызываемой” процедуре используются копии переменных, передаваемые “вызывающей” процедурой в списке параметров. “Вызываемая” процедура не может изменить значение переданной ей переменной в “вызывающей” процедуре. К параметрам-значениям применяются обычные правила преобразования данных. Реально передаваемые параметры-значения преобразуются к типу данных, указанному в прототипе данной процедуры. Допустимые типы параметров-значений:
BYTE SHORT USHORT LONG ULONG SREAL REAL DATE TIME STRING
Пример:
MAP
MODULE('Test')
MyProc1 PROCEDURE(LONG
) ! Параметр-значение типа LONGMyProc2 PROCEDURE(<LONG>
) ! Параметр-значение типа LONG, который может опускатьсяMyProc3 PROCEDURE(LONG=23)
! Если параметр опущен, то передать 23MyProc4 PROCEDURE(LONG Count, REAL Sum
) ! Параметр типа LONG имеет имя Count, а! параметр типа REAL имеет имя Sum
MyProc5 PROCEDURE(LONG Count=1, REAL Sum=0
)!Значение по умолчанию параметра Count равно!1, а параметра Sum равно 0
END
MODULE('Party3.Obj')
Func48 PROCEDURE(REAL),REAL,PASCAL !
передача параметров как в ПаскалеFunc49 PROCEDURE(SREAL
),REAL,C,NAME('_func49')!передача параметров как в C и внешнее имя.END
END
Параметры-переменные
Параметры-переменные
являются “передаваемыми по адресу”. Переменные, передаваемые по адресу, имеют в памяти только одно местоположение. Изменение значения переменной в “вызываемой” процедуре изменяет его также и в “вызывающей”. Типы данных параметров-переменных приводятся в списке параметров прототипа процедуры или функции в структуре MAP со звездочкой (*) перед названием типа. Допустимые параметры-переменные:*BYTE *SHORT *USHORT *LONG *ULONG *SREAL *REAL *BFLOAT4 *BFLOAT8
*DECIMAL *PDECIMAL *DATE *TIME *STRING *PSTRING *CSTRING *GROUP
Пример:
MAP
MODULE('Test')
MyProc2 PROCEDURE(<*LONG>
) ! Параметр-переменная типа LONGMyFunc1 PROCEDURE(*SREAL
),REAL,C ! Параметр-переменная типа SREAL, возвращается REAL,! передача параметров как в C
MyProc6 PROCEDURE(CONST *CSTRING Value
) !Значение сохраняет постоянную величину в!процедуре
END
MODULE('Party3.Obj')
Func4 PROCEDURE(*CSTRING
),REAL,C,RAW ! В функцию на С передается только адрес строки! типа CSTRING
Func47 PROCEDURE(*CSTRING
),CSTRING,C,RAW ! возвращает указатель на CSTRINGEND
END
Передача массивов в качестве параметров
Чтобы предать в качестве параметра массив, в прототипе должен быть объявлен тип данных массива как параметр-переменная (“передаваемая по адресу”), с пустым списком индексов. Если массив более чем одномерный, то чтобы обозначить число измерений в нем, в списке индексов запятыми разделяются позиции по числу измерений. При обращении в процедуру должен передаваться целый массив, а не один элемент.
Пример:
MAP
MainProc PROCEDURE
AddCount PROCEDURE(*LONG[,] Total,*LONG[,]
Current) ! Передача двух двумерных массивов! типа LONG
END
CODE
MainProc ! Вызов первой процедуры
MainProc PROCEDURE
TotalCount LONG,DIM(10,10)
CurrentCnt LONG,DIM(10,10)
CODE
AddC
ount(TotalCount,CurrentCnt) ! Обратиться к процедуре, передав массивAddCount PROCEDURE(*LONG[,] Total,*LONG[,] Current) ! Процедура ожидает передачи двух
! массивов
CODE
LOOP I# = 1 TO MAXIMUM(Total,1) ! Цикл по первому индексу
LOOP J# = 1 TO MAXIMUM(To
tal,2) ! Цикл по второму индексуTotal[I#,J#] += Current[I#,J#] ! увеличить TotalCount из CurrentCnt
END
END
CLEAR(Current) ! Очистить массив CurrentCnt
Передача параметров с неопределенным типом данных
Используя нетипизированные параметры-значения и нетипизированные параметры-переменные, можно писать обобщенные процедуры, которые выполняют действия над переданными им параметрами в ситуации, когда точный тип параметра может изменяться от одного обращения к процедуре к другому. Это полиморфные параметры; в зависимости от типа передаваемых в процедуру данных, они могут приобретать любой другой простой тип данных.
Нетипизированные параметры-значения представляются в прототипе процедуры знаком вопроса (?). При выполнении процедуры, параметр динамически обретает тип и действует как объект данных базового типа передаваемой переменной (LONG, DECIMAL, STRING или REAL) или переменной, которой он последний раз был присвоен. Это означает, что этот “подразумеваемый” тип данных параметра можно изменить внутри процедуры, что позволяет его рассматривать как параметр любого типа данных.
Нетипизированные параметры-значения передаются в процедуру “по значению”, а его “подразумеваемый” тип данных подчиняется правилам преобразования данных, принятым в Clarion. Как нетипизированные параметры-значения могут передаваться переменные следующих типов данных:
BYTE SHORT USHORT LONG ULONG SREAL REAL BFLOAT4 BFLOAT8 DECIMAL PDECIMAL DATE TIME STRING PSTRING CSTRING GROUP (
трактуемый как STRING) Нетипизированное параметр-значение (?) Нетипизированная параметр-переменная(*?)Если нетипизированный параметр-значение передается во внешнюю библиотечную функцию, написанную не на языке Clarion, то можно использовать для него атрибут RAW. Это вызовет преобразование данных к типу LONG и затем передачу данных как параметр “void *” в С/С++ (что исключает появление предупреждения о “несовместимости типов”).
Нетипизированные параметры-переменные представляются в прототипе процедуры звездочкой и знаком вопроса (*?). Внутри процедуры параметр с типом переменной действует как объект такого же типа данных, что и переменная в вызывающей процедуре, чье значение передается данным параметром. Это означает, что во время выполнения процедуры тип данных параметра не изменяется.
Нетипизированные параметры-переменные передаются в процедуру “по адресу”. Таким образом, любые изменения, выполненные над переданным параметром, производятся непосредственно над переменной из вызывающей процедуры, использовавшейся в качестве параметра. Параметры с неопределенным типом позволяют писать полиморфные процедуры.
Внутри процедуры, которая получает параметры с нетипизированной параметром-переменной, делать какие-либо предположения о типе данных принятого параметра небезопасно. Опасность такого предположения заключается в том, что существует вероятность присвоения значения, выходящего за границы допустимого для переданного параметра диапазона. Если это происходит, то результат может существенно отличаться от ожидаемого.
Смотри также:
ANY (любой простой тип данных)В качестве нетипизированных параметров-переменных могут передаваться данные следующих типов:
BYTE SHORT USHORT LONG ULONG SREAL REAL BFLOAT4 BFLOAT8 DECIMAL
PDECIMAL DATE TIME STRING PSTRING CSTRING Нетипизированная параметр-переменная (*?)
Если нетипизированный параметр-переменная (*?) передается во внешнюю библиотечную функцию, написанную не на языке Clarion, то можно указать атрибут RAW. В таком случае это эквивалентно передаче параметра “void*” в C/C++.
Массив нельзя передавать ни в одной из форм параметров с неопределенным типом.
Пример:
PROGRAM
MAP
Proc1 PROCEDURE(?
) ! Нетипизированный параметр-значениеProc2 PROCEDURE(*?
) ! Нетипизированный параметр-переменнаяProc3 PROCEDURE(*?
) ! Нетипизированный параметр-переменная!(установить для зацикливания)
Max PROCEDURE(?,?),?
! Процедура, возвращающая нетипизированную! параметр-переменную
END
GlobalVar1 BYTE(3) ! Начальное значение = 3
GlobalVar2 DECIMAL(8,2,3)
GlobalVar3 DECIMAL(8,1,3)
MaxInteger LONG
MaxString STRING(255)
MaxFloat REAL
CODE
Proc1(GlobalVar1) ! Передать байт равный 3
Proc2(GlobalVar2) ! Передать в процедуру DECIMAL(8,2),
! значение равно 3.00 – выдаст 3.33
Proc2(GlobalVar3) ! Передать в процедуру DECIMAL(8,1),
! значение равно 3.0 - выдаст 3.3
Proc3(GlobalVar1) ! Передать в процедуру байт и наблюдать,
! как она зациклится
MaxInteger = Max(1,5) ! Процедура Max возвращает 5
MaxString = Max('Z','A') ! Процедура Max возвращает 'Z'
MaxFloat = Max(1.3,1.25) ! Процедура Max возвращает 1.3
Proc1 PROCEDURE(? ValueParm)
CODE ! ValueParm начинается с 3 и является LONG
ValueParm = ValueParm & ValueParm ! теперь содержит 33 (ValueParm - строка)
ValueParm = ValueParm / 10 ! теперь содержит 3.3 (ValueParm - REAL)
Proc2 PROCEDURE(*? VariableParm)
CODE
VariableParm = 10 / 3 ! Присвоить 3.333333... переданной переменной
Proc3 PROCEDURE(*? VariableParm)
CODE
LOOP
IF VariableParm > 250 THEN BREAK. ! Если передана переменная типа BYTE, то цикл
!бесконечный
VariableParm += 10
END
Max PROCEDURE(Val1,Val2) ! Найти большее из двух переданных значений
CODE
IF Val1 > Val2 ! Сравнить первое значение со вторым
RETURN(Val1) ! и вернуть его, если оно больше
ELSE ! иначе
RETURN(Val2) ! вернуть второе
END
Смотри также:
MAP, MEMBER, MODULE, PROCEDURE, CLASS
Параметры-объекты
Параметры-объекты
передают имя структуры данных в “вызываемую” процедуру. Передача объекта позволяет “вызываемой” процедуре использовать те команды Clarion, которые требуют указания метки структуры в качестве параметра. В прототипе процедуры в структуре MAP параметры-объекты указываются именем объекта. Параметры-объекты всегда “передаются по адресу”. Допустимые параметры-объекты:FILE VIEW KEY INDEX QUEUE WINDOW REPORT BLOB
REPORT может быть передан как параметр прототипированной процедуре, получающей WINDOW, так как внутренне они используют одинаковую структуру.
Пример:
MAP
MODULE('Test')
MyFunc2 PROCEDURE(FILE
),STRING ! Параметр-объект FILE, возвращается строкаProcType PROCEDURE(FILE
),TYPE ! Определение типа параметра-процедурыMyFunc4 PROCEDURE(FILE
),STRING,PROC ! Можно обращаться как к процедуре (не будет! предупреждения)
MyProc6 PROCEDURE(FILE
),PRIVATE ! Может вызываться другими процедурами только модуля! TEST.CLW
END
END
Параметры-процедуры
Параметры-процедуры
передают в “вызываемую” процедуру имя другой процедуры. В прототипе процедуры в структуре MAP параметры-процедуры представляются именем ранее объявленного прототипа такого же типа (который может иметь атрибут TYPE, а может и не иметь). При обращении в программе к “вызываемой” процедуре ей должно передаваться имя процедуры, которая имеет точно такой же прототип, какой имеет процедура, указанная в прототипе “вызываемой” процедуры.За каждым параметром в списке может следовать допустимая в языке Clarion метка, которая совершенно игнорируется компилятором. Эта метка используется исключительно в целях документирования параметров, чтобы сделать прототип более удобочитаемым или чтобы продублировать определение процедуры. Каждое определение передаваемого параметра может иметь постоянное значение, соответствующее типу данных (или метке, если она есть), используемое по умолчанию, которое передается, когда параметр опущен.
Пример:
MAP
MODULE('Test')
ProcType PROCEDURE(FILE),TYPE ! Определение типа параметра-процедуры
MyFunc3 PROCEDURE(ProcType
),STRING ! Процедура-параметр типа ProcType, возвращает STRING,!должна передаваться процедура, принимающая объект FILE
!в качестве параметра
END
END
Передача “поименованных” структур GROUP, QUEUE и CLASS
Передача структуры GROUP как параметра-переменной или QUEUE как параметра-объекта в процедуру не позволяет в вызванной процедуре обращаться к полям - компонентам этих структур. Однако чтобы передавать адрес параметра и обеспечить доступ к полям - компонентам этих структур, можно указать в списке параметров прототипа метку структуры GROUP или QUEUE. Таким же образом можно “поименовать” класс, чтобы обеспечить принимающей процедуре возможность доступа к элементам данных и методам класса.
Для того чтобы обращаться к составляющим структуру полям поместите метку структуры GROUP, QUEUE или структуру CLASS в список прототипируемых параметров процедуры. Параметр передается “по адресу” и позволяет получающей процедуре ссылаться на поля компонентов структуры (общие методы CLASS работают таким же образом).
Структура передаваемых данных всегда должна совпадать с определением, так же как и типы данных составляющих полей. Передаваемая группа или очередь может быть “надмножеством” поименованного параметра, если только идущие впереди поля совпадают соответствующими полями поименованной структуры GROUP или QUEUE. Реально передаваемый класс также может быть производным от поименованного класса. “Экстра” поля в GROUP, QUEUE или CLASS недоступны для использования в получающей процедуре.
Для структур GROUP, QUEUE или CLASS, указанных именем в списке параметров, атрибут TYPE не нужен, и их не нужно объявлять раньше, чем структуру MAP. Однако они должны быть объявлены раньше, чем процедура будет принимать их в качестве параметров при вызове. Это единственный случай в языке Clarion, когда разрешается такая “ссылка вперед”.
Используйте синтаксис Уточнения имени переменной, чтобы ссылаться на компоненты переданной группы в получающей процедуре (LocalName.MemberName). На поля компонентов в структуре ссылаются с помощью имен, данных им в группе, названной так же, как и тип данных в прототипе, а не имена полей в фактически переданной структуре. Это позволяет получающей процедуре быть общей, вне зависимости от того, какая структура данных передается в нее на самом деле.
Пример:
PROGRAM
MAP
MyProc PROCEDURE
AddQue PROCEDURE(PassGroup PassedGroup, NameQue PassedQue)
END ! Принимает GROUP описанную так же
!как PassGroup и QUEUE
! определенную так же как NameQue
PassGroup GROUP,TYPE ! Определение типа - память не выделяется
F1 STRING(20) ! группа с 2-мя полями STRING(20)
F2 STRING(20)
END
NameGroup GROUP ! Имя группы
First STRING(20) ! первое имя
Last STRING(20) ! последнее имя
Company STRING(30) ! Это “Экстра” поле недоступно для
! получающей процедуры
END ! (процедура(AddQue) с PassGroup имеет два поля
NameQue QUEUE,TYPE ! Определение типа Name Queue –
! память не выделяется
First STRING(20)
Last STRING(20)
END
CODE
MyProc
MyProc PROCEDURE
LocalQue NameQue ! Local Name Queue объявляется как NameQue
CODE
NameGroup.First = 'Fred'
NameGroup.Last = 'Flintstone'
AddQue(NameGroup,LocalQue) ! Передача NameGroup и LocalQue процедуре AddQue
NameGroup.First = 'Barney'
NameGroup.Last = 'Rubble'
AddQue(NameGroup,LocalQue)
NameGroup.First = 'George'
NameGroup.Last = 'O''Jungle'
AddQue(NameGroup,LocalQue)
LOOP X# = 1 TO RECORDS(LocalQue) !Проверить, что есть в LocalQue сейчас
GET(LocalQue,X#)
MESSAGE(CLIP(LocalQue.First) & ' ' & LocalQue.Last)
END
AddQue PROCEDURE(PassGroup PassedGroup, NameQue PassedQue)
CODE
PassedQue.First = PassedGroup.F1 ! Актуально: LocalQue.First = NameGroup.First
PassedQue.Last = PassedGroup.F2 ! Актуально: LocalQue.Last = NameGroup.Last
ADD(PassedQue)
! Добавить элемент в очередь PassedQue (LocalQue)ASSERT(NOT ERRORCODE())
Смотри также:
MAP, MEMBER, MODULE, PROCEDURE, CLASS
Типы значений, возвращаемых функциями
Процедура объявленная как процедура, возвращающая значение, должна возвращать значение. Тип возвращаемого значения приводится после необязательного списка параметров, отделенный от него запятой. Допустимые типы возвращаемых значений:
BYTE SHORT USHORT LONG ULONG SREAL REAL DATE
TIME STRING нетипизированное значение - параметр (?)
Нетипизированное возвращаемое значение (?) означает, что тип данных возвращаемого процедурой значения неизвестен. Нетипизированное возвращаемое значение работает точно таким же образом, как и нетипизированный параметр-значение. Когда возвращаемое процедурой значение подпадает под стандартные правила преобразования типов, то не имеет значения, какого типа данные вернулись.
Возвращаемые типы переменных:
CSTRING *STRING *BYTE *SHORT *USHORT *LONG
*ULONG *SREAL *REAL *DATE *TIME
нетипизированная переменная - параметр(?)
Возвращаемые типы переменных даны лишь для составления внешних библиотечных функций (написанных на другом языке), которые возвращают только адрес данных - они не используются в процедурах языка Clarion.
В прототипе функций, которые возвращают указатель (адрес данных), типу возвращаемого значения (за исключением CSTRING) должна предшествовать звездочка (*). Во время выполнения программы необходимые действия с возвращенным указателем выполняются автоматически. Функции, прототипированные таким способом, действуют точно так же, как определенные в программе переменные - когда в тексте Clarion-программы используется такая функция, автоматически используются данные, адрес которых возвращен функцией. Эти данные можно присвоить другим переменным, передать в качестве параметров процедурам или получить их адрес с помощью функции ADDRESS.
Тип данных CSTRING является исключением, так как все другие типы данных имеют фиксированную длину, а CSTRING - нет. Поэтому, любую функцию на С, возвращающую указатель на CSTRING, можно прототипировать в С как “char *”, но компилятор копирует элемент данных в стек. Поэтому, точно также
как в случае других значений, возвращаемых посредством указателей, при использовании функции в тексте программы на языке Clarion данные, на которые указывает возвращенный функцией указатель, используются автоматически (указатель разыменовывается).В качестве примера предположим, что функция XYZ() возвращает *CSTRING (указатель на CSTRING), переменная CStringVar имеет тип CSTRING, а переменная LongVar имеет тип LONG. Простой оператор присваивания языка Clarion: CStringVar =XYZ() поместит данные, указанные адресом, который возвратит функция XYZ() в переменную CStringVar. Оператор LongVar = ADDRESS(XYZ()), поместит адрес данных в переменную LongVar.
Нетипизированный параметр-переменная (*?), возвращающая значение, указывает, что тип данных переменной, возвращаемый процедурой, неизвестен. Это происходит тем же образом, что и в случае нетипизированного параметра-переменной.
Ссылочные типы RETURN:
*FILE *KEY *WINDOW *VIEW
Именованный CLASS (*
ClassName)Именованный QUEUE (*
QueueName)PROCEDURE может вернуть ссылку, которая может быть либо закреплена за ссылочной переменной, либо использована в списке параметров там, где присутствие объекта ссылки будет естественным. PROCEDURE, которая возвращает *WINDOW, также может вернуть метку структуры APPLICATION либо REPORT.
Пример:
MAP
MODULE('Party3.Obj') ! Библиотека сторонней фирмы
Func46 PROCEDURE(*CSTRING),REAL,C,RAW
! В функцию на С передается только адрес данных,! возвращается Real
Func47 PROCEDURE(*CSTRING),CSTRING,C,RAW
! Возвращается указатель на CSTRING
Func48 PROCEDURE(REAL),REAL,PASCAL
! Передача параметров по типу PASCAL, возвращается Real.
Func49 PROCEDURE(SREAL),REAL,C,NAME('_func49')
! Передача параметров по типу C и внешнее имя функции, возвращается Real
END
END
Смотри также:
MAP, MEMBER, MODULE, NAME, PROCEDURE, RETURN, Переменные-указатели
C, PASCAL (соглашения о связях)
C
PASCAL
Атрибуты
C и PASCAL в прототипе процедуры указывают, что параметры всегда передается через стек. В языке С параметры помещаются в стек справа налево по списку параметров, в то время как в Паскале наоборот, слева направо. Паскаль также полностью совместим с соглашениями о связях интерфейса прикладного программирования (API) Windows для 32-х разрядных приложений, эти соглашения стали соглашениями, используемыми по умолчанию операционной системой (и также запрещает “усечение” имен).Соглашения о связях обеспечивают совместимость с библиотеками сторонних фирм, написанных на других языках (если они компилировались компиляторами TopSpeed). Если в прототипе не указать тип соглашений о связях, то по умолчанию будет использоваться внутреннее, принятое в компиляторах семейства TopSpeed соглашение, основанное на передаче параметров в регистрах.
Пример:
MAP
MODULE('Party3.Obj') ! Библиотека сторонней фирмы
Func46 PROCEDURE(*CSTRING,*REAL),REAL,C,RAW ! Передавать в функцию написанную
! на С только адрес CSTRING
Func49 PROCEDURE(*CSTRING,*REAL),REAL,PASCAL,RAW ! Передавать CSTRING, затем REAL, !только адрес
END
END
Смотри также:
Прототипы процедур, Списки параметров в прототипах
DERIVED (предотвращает перегрузку функции)
DERIVED
Атрибут
DERIVED в прототипе процедуры указывает, что процедура, для которой он установлен, является виртуальной процедурой. Он может использоваться самостоятельно или дополнительно к атрибуту VIRTUAL в прототипе.Используйте DERIVED, чтобы принудительно вызвать ошибку компиляции, если найдено несоответствие прототипов между производным виртуальным методом и его родителем. Это предотвращает перегрузку процедуры при использовании виртуальной процедуры.
Пример:
ClassA CLASS
Method1 PROCEDURE(LONG, <LONG>)
END
ClassB CLASS(ClassA)
Method2 PROCEDURE(LONG,<LONG>),DERIVED
END
ClassC CLASS(ClassA)
Method3 PROCEDURE(LONG,<LONG>),VIRTUAL,DERIVED
END
ClassD CLASS(ClassA)
Method4 PROCEDURE(STRING),DERIVED
!Вызовет ошибку компиляцииEND
Смотри также:
CLASS, VIRTUAL
DLL (процедура определена внешне, в библиотеке DLL)
DLL(
флаг ] )DLL
Объявляет процедуру или функцию, определенную внешне, в библиотеке DLL.флаг
Числовая константа, метка соответствия, или определение системы поддержки проекта, которое задает, активен ли данный атрибут. Если флаг установлен в 0, то этот атрибут неактивен, как если бы его вообще не было. Если флаг имеет отличное от нуля значение, то атрибут активен. Флаг может быть неопределенной меткой, и в этом случае атрибут считается активным.Атрибут DLL указывает, что процедура, в прототипе которой имеется этот атрибут, определена в библиотеке с динамическими связями (DLL). Для 32-битовых приложений атрибут DLL обязателен, так как такие библиотеки являются настраиваемыми (перемещаемыми) в 32-битовом адресном пространстве, которое требует от компилятора еще одного дополнительного разыменовывания (преобразования адреса) при обращении к процедуре.
Пример:
MAP
MODULE('STDFuncs.DLL') ! DLL - библиотека стандартных функций
Func50 PROCEDURE(SREAL),REAL,PASCAL,DLL(dll_mode) !
END
END
Смотри также:
EXTERNAL
NAME (установить внешнее имя для прототипируемой процедуры)
NAME(
константа )NAME
Указать компоновщику “внешнее” имяконстанта Строковая константа. Регистр букв имеет значение.
Атрибут
NAME задает внешнее имя, используемое компоновщиком. Этот атрибут может указываться в прототипе процедуры. Параметр константа содержит внешнее имя, используемое компоновщиком для того, чтобы подключить процедуру или функцию из внешней библиотеки или для предоставления прототипам языка Clarion внешних имен для внешних связей (обычно для устранения искажений стандартного имени компилятора), что облегчает составление экспортного листа для .DLL, используемого в других проектах языка.Пример:
PROGRAM
MAP
MODULE('External.Obj')
AddCount PROCEDURE(LONG),LONG,C,NAME('_AddCount') !
Функция на C называющаяся ‘AddCount’END
END
Смотри также:
Прототипы процедур, Образование Имен и С++ Совместимость
PRIVATE (использование процедуры ограничено классом или модулем)
PRIVATE
Атрибут
PRIVATE указывает, что к процедуре, в прототипе которой он помещен, можно обращаться из процедур этого же самого исходного модуля. Тем самым она скрывается от процедур других модулей.Обычно этот атрибут указывается в прототипах методов в структурах CLASS, и поэтому к методу можно обращаться из других методов класса в данном модуле. Частные методы не наследуются классами производными от классов, содержащих прототип частного метода, хотя они могут быть виртуальными методами, если производный класс содержится в этом же модуле.
Пример:
MAP
MODULE('STDFuncs.DLL') ! Стандартные функции .DLL
Func49 PROCEDURE(SREAL),REAL,PASCAL,PROC
Proc50 PROCEDURE(SREAL),PRIVATE !
Вызов только из Func49END
END
OneClass CLASS,MODULE('OneClass.CLW'),TYPE
BaseProc PROCEDURE(REAL Parm) ! Общий метод
Proc PROCEDURE(REAL Parm),PRIVATE
! Объявить метод частнымEND
TwoClass OneClass !Пример класса OneClass
CODE
TwoClass.BaseProc(1) ! Корректный вызов BaseProc
TwoClass.Proc(2) ! Некорректный вызов Proc в OneClass.CLW:
MEMBER()
OneClass.BaseProc PROCEDURE(REAL Parm)
CODE
SELF.Proc(Parm) ! Корректный вызов Proc
OneClass.Proc PROCEDURE(REAL Parm)
CODE
RETURN(Parm)
Смотри также:
CLASS
PROC (нет предупреждения, что функция вызывается как процедура)
PROC
Атрибут
PROC может быть размещен в прототипе процедуры, которая возвращает значение. Это позволяет использовать обычный вызов процедуры, а не только в выражениях и присваиваниях в тех случаях, когда нет нужды использовать возвращаемое значение. Атрибут PROC предупреждает сообщения компилятора, которые обычно в таких случаях вы получаете.Пример:
MAP
MODULE('STDFuncs.DLL') ! Стандартные функции .DLL
Func50 PROCEDURE(SREAL),REAL,PASCAL,PROC
END
END
Смотри также:
PROCEDURE
PROTECTED (установить процедуру частной по отношению к CLASS
или дочернему CLASS )
PROTECTED
Атрибут
PROTECTED указывает на то, что процедура, в чьем прототипе он помещен, является видимой только для тех процедур, которые объявлены в той же самой структуре CLASS (методах этого CLASS) и методах любого дочернего CLASS. Это предохраняет PROCEDURE от возможного вызова со стороны кода, внешнего по отношению к CLASS, в котором она определена, или последовательности дочерних классов.Пример:
OneClass CLASS,MODULE('OneClass.CLW'),TYPE
BaseProc PROCEDURE(REAL Parm) ! Общий метод
Proc PROCEDURE(REAL Parm),PROTECTED
!Объявление защищенного методаEND
TwoClass OneClass ! Экземпляр OneClass
ThreeClass CLASS(OneClass),MODULE('ThreeClass.CLW') ! Дочерний от OneClass
ThreeProc PROCEDURE(REAL Parm) ! Объявление общего метода
END
CODE
TwoClass.BaseProc(1) ! Корректный вызов BaseProc
TwoClass.Proc(2) ! Некорректный вызов Proc в OneClass.CLW:
MEMBER()
OneClass.BaseProc PROCEDURE(REAL Parm)
CODE
SELF.Proc(P
arm) ! Корректный вызов ProcOneClass.Proc PROCEDURE(REAL Parm)
CODE
RETURN(Parm)
!В ThreeClass.CLW:
MEMBER()
ThreeClass.NewProc PROCEDURE(REAL Parm)
CODE
SELF.Proc(Parm) ! Корректный вызов Proc
Смотри также:
CLASS
RAW
Атрибут RAW задает в прототипе процедуры для передаваемых в качестве параметров групп и строк передачу только их адреса памяти. Он позволяет для параметров типа *?, STRING или GROUP передавать в процедуру или функцию, написанную не на языке Clarion, только адрес памяти, независимо от того передаются ли параметры по адресу или по значению. Обычно, для параметров типа STRING или GROUP передается адрес и длина строки. Указание атрибута RAW исключает передачу длины. В случае прототипа с параметром неопределенного типа (?) параметр воспринимается как LONG, но передается как “void *”, что исключает появление предупреждений компоновщика. Этот атрибут введен для того, чтобы обеспечить совместимость с внешними библиотечными функциями, которые при вызове ожидают передачи только адреса строки.
Если функция прототипирована для возврата значения одним из следующих типов: ?, *? или *STRING, и прототип имеет атрибут RAW, то возвращаемое значение будет трактоваться как LONG.
Пример:
MAP
MODULE('Party3.Obj') ! Библиотека сторонней фирмы
Func46 PROCEDURE(*CSTRING),REAL,C,RAW ! Передавать в функцию, написанную на С только
END ! адрес CSTRING
END
Смотри также:
Прототипы процедур, Списки параметров в прототипах
REPLACE (установить конструктор или деструктор замены)
REPLACE
Атрибут
REPLACE указывает, что PROCEDURE, в чьем прототипе он помещен, полностью заменяет конструктор или деструктор родительского класса. REPLACE действителен только в PROCEDURE с меткой “Construct” или “Destruct” и объявленной в структуре CLASS, дочерней для класса, также содержащего упоминание “Construct” или “Destruct”. Если меткой PROCEDURE является “Construct”, то методом является Конструктор, автоматически вызываемый при подтверждении объекта. Объект подтверждается при вхождении в область видимости или при создании оператором NEW. Если меткой PROCEDURE является “Destruct”, то методом - Деструктор, автоматически вызываемый при уничтожении объекта. Объект уничтожается при выходе из области видимости или при уничтожении оператором DISPOSE.Пример:
PROGRAM
SomeQueue QUEUE,TYPE
F1 STRING(10)
END
OneClass CLASS,MODULE('OneClass.CLW'),TYPE
ObjectQueue &SomeQueue ! Объявление ссылки на поименованную очередь
Construct PROCEDURE ! Объявление Конструктора
Destruct PROCEDURE ! Объявление Деструктора
END
TwoClass CLASS(OneClass),MODULE('TwoClass.CLW'),TYPE
Construct PROCEDURE,REPLACE
! Объявление замены ConstructorEND
MyClass OneClass ! Экземпляр OneClass
YourClass &TwoClass ! Ссылка на TwoClass
CODE ! Появление объекта MyClass
! вызов OneClass.Construct
YourClass &= NEW(TwoClass) ! Появление объекта YourClass
! вызов TwoClass.Construct
DISPOSE(YourClass) ! Завершение объекта YourClass
! вызов OneClass.Destruct
RETURN ! Завершение объекта MyClass
! вызов OneClass.Destruct
! OneClass.CLW содержит
OneClass.Construct PROCEDURE
CODE
SELF.ObjectQueu
e = NEW(SomeQueue) !Создание очереди объектовOneClass.Destruct PROCEDURE
CODE
FREE(SELF.ObjectQueue) ! очистить очередь объектов
DISPOSE(SELF.ObjectQueue) ! и удалить очередь
!TwoClass.CLW содержит:
TwoClass.Construct PROCEDURE
CODE
SELF.ObjectQueue = N
EW(SomeQueue) ! Создание очереди объектовSELF.ObjectQueue.F1 = 'First Entry'
ADD(SELF.ObjectQueue)
Смотри также:
NEW, DISPOSE, CLASS
TYPE (задать определение типа процедуры)
TYPE
Атрибут TYPE задает прототип, который не является ссылкой на реальную процедуру. Вместо этого, он определяет имя прототипа, которое должно использоваться в других прототипах для обозначения типа процедуры, передаваемой в другую процедуру в качестве параметра.
Когда имя типизированного прототипа используется в списке параметров другого прототипа, процедура, которую этот другой прототип представляет, будет принимать в качестве параметра метку оператора PROCEDURE, которая имеет точно такой же список параметров (и такое же возвращаемое значение, если она возвращает значение), что и типизированный прототип.
Пример:
MAP
ProcType PROCEDURE(FILE),TYPE
! Определение типа процедуры-параметраMyFunc3 PROCEDURE(ProcType),STRING ! Параметр - процедура, возвращается
!строка
!должна передаваться метка
!процедуры, которая принимает
! в качестве параметра файл
END
Смотри также:
Прототипы процедур, Списки параметров в прототипах
VIRTUAL (установить, что метод виртуальный)
VIRTUAL
Атрибут VIRTUAL указывает, что процедура, в прототипе которой он задан, является виртуальным методом структуры CLASS, содержащий этот прототип. Этот атрибут позволяет методам родительского класса обращаться к методам дочернего класса. Атрибут VIRTUAL нужно поместить и в прототип метода родительского класса, и в прототип метода производного класса.
Пример:
OneClass CLASS ! Базовый класс
BaseProc PROCEDURE(REAL Parm) ! Не виртуальный метод
Proc PROCEDURE(REAL Parm),VIRTUAL
! Объявить виртуальный методEND
TwoClass CLASS(OneClass) ! Производный от OneClass класс
Proc PROCEDURE(REAL Parm),VIRTUAL
! Объявить виртуальный методEND
ClassThree OneClass ! Другой экземпляр объекта класса OneClass
ClassFour TwoClass ! Другой экземпляр объекта класса TwoClass
CODE
OneClass.BaseProc(1) ! BaseProc обращается к OneClass.Proc
TwoClass.BaseProc(2) ! BaseProc обращается к TwoClass.Proc
ClassThree.BaseProc(3) ! BaseProc обращается к OneClass.Proc
ClassFour.BaseProc(4) ! BaseProc обращается к TwoClass.Proc
OneClass.BaseProc PROCEDURE(REAL Parm)
CODE
SELF.Proc(Parm) ! Обращение к виртуальному методу, или OneClass.Proc
! или TwoClass.Proc, в зависимости от того, какой
! экземпляр объекта выполняется
Смотри также:
CLASS
Перегрузка процедур означает возможность в нескольких определениях процедур использовать одно и то же имя процедуры. Это одна из форм полиморфизма. Для того чтобы сделать возможными одинаковые имена, каждая такая процедура должна получать различные параметры так, чтобы, основываясь на списке параметров, компилятор мог определить, к какой процедуре осуществляется обращение
.Идея состоит в том, чтобы разрешить использование одного и того же имени для нескольких процедур, имеющих разные прототипы так, что можно выполнять особые (но обычно похожие) действия над данными разных типов. С точки зрения эффективности, Перегрузка процедур предпочтительней, чем кодирование простой процедуры с параметрами, которыми можно пренебречь; для этих целей можете получать (а можете - нет) множественные параметры.
В языке Clarion также имеются полиморфные функции, для которых используются параметры “?” и “*?”, однако Перегрузка процедур расширяет этот полиморфизм, чтобы еще включать параметры-объекты и параметры “поименованные группы”.
Одним из примеров перегрузки функций может служить оператор OPEN языка Clarion, который инициализирует объект для последующего использования в программе. В зависимости от того, объект какого типа ему передан (файл, окно, структура VIEW и т.д.) он выполняет похожие, но физически различные действия.
Смотри также:
Правила перегрузки процедур, Образование Имен и С++ Совместимость
В языке Clarion имеется встроенное преобразование типов данных, что может затруднить для компилятора реализацию перегрузки. Поэтому есть правила, обуславливающие реализацию компилятором перегрузки функций. Эти правила применяются в следующем порядке:
1. Параметры-объекты приводятся к объектам FILE, KEY, WINDOW и QUEUE. Если уже после этого можно выбрать прототип, то компилятор это и делает (под это правило попадают большинство встроенных процедур Clarion). Заметим, что KEY и VIEW неявно происходят от FILE, в то время как APPLICATION и REPORT - от WINDOW.
2. Все параметры “поименованные группы” должны соответствовать друг другу по своей структуре. Параметры-процедуры соответствуют по структуре. Классы должны соответствовать по именам, а не просто по структуре.
3. Прототипы должны соответствовать по числу и порядку следования обязательных параметров. Это третий (а не первый) фактор, по которому обычно компилятор может решить, какой прототип пользователь имел в виду или выдать наиболее осмысленное сообщение об ошибке.
4. Если соответствующий прототип не найден, то допускается соответствие производных объектов. В этот момент допускается, что KEY может соответствовать FILE, а группа, которая предполагается производной, должна соответствовать одному из базовых классов. Если одно предположение о производности объекта не срабатывает, делается следующее и так до трех раз. Теперь все QUEUE соответствуют очередям и группам и т.п. Прежде остальных типов параметров устанавливается происхождение классов.
5. Параметры-переменные (непоименованные) должны точно соответствовать типам реально передаваемых данных. *GROUP соответствует *STRING. ANY параметр-переменная соответствует *?
6. Все параметры значения считаются имеющими один и тот же тип.
Пример:
MAP
Func PROCEDURE(WINDOW) ! 1
Func PROCEDURE(FILE) ! 2
Func PROCEDURE(KEY) ! 3
Func PROCEDURE(FILE,KEY) ! 4
Func PROCEDURE(G1) ! 5
Func PROCEDURE(G0) ! 6
Func PROCEDURE(KEY,G0) ! 7
Func PROCEDURE(FILE,G1) ! 8
Func PROCEDURE(SHORT = 10) ! 9
Func PROCEDURE(LONG) ! 10
Func PROCEDURE()
! Неправильно, неотличимо от 9Func PROCEDURE(*SHORT) ! 11
Func1 PROCEDURE(*SHORT)
Func1a PROCEDURE(*SHORT)
Func2 PROCEDURE(*LONG)
Func PROCEDURE(Func1) ! 12
Func PROCEDURE(Func1a) ! Неправильно, то же, что и 12
Func PROCEDURE(Func2) ! 13
END
G0 GROUP
END
G1 GROUP(G0)
END
CODE
Func(A:Window) ! Обращение к 1 по правилу 1
Func(A:File) ! Обращение к 2 по правилу 1
Func(A:Key) ! Обращение к 3 по правилу 1
Func(A:View) ! Обращение к 2 по правилу 4
Func(A:Key,A:Key) ! Обращение к 4 по правилу 4 (следовало бы обратиться
! к функции с параметрами key,key, если бы она была)
Func(A:G0) ! Обращение к 6 по правилу 2
Func(A:G1) ! Обращение к 5 по правилу 2
Func(A:Func2) ! Обращение к 13 по правилу 2
Func(A:Key,A:G1) ! Ошибка - неопределенность. Если использовать правило
!4, то подходят и 7 и 8
Func(A:Short) ! Ошибка - неопределенность. Обращение к 9 или 11
Func(A:Real) ! Обращение к 9 по правилу 6
Func ! Обращение к 9 по правилу 3
Смотри также:
CLASS
Образование имен и совместимость с C++
Каждая перегружаемая функция будет иметь для компоновки имя, составленное из имени процедуры и “усеченного” списка аргументов (атрибут NAME может причинить вред усечению имени). Образование имен разработано так, чтобы обеспечить некоторую степень перекрестных обращений между C++ и Clarion. Со стороны C++ необходимо указать:
#pragma name(prefix=>” “)
и имена, состоящие из прописных букв. Со стороны Clarion нужно иметь структуру MODULE со строкой нулевой длины в качестве параметра:
MODULE(‘ ‘)
END
Перекрестные обращения возможны только между теми процедурами, прототипы, которых содержат только типы данных, приведенные в следующем списке. Кларионовские параметры-переменные (передаваемые посредством адреса) соответствуют параметрам ссылок в С, если не указано что они могут опускаться, в этом случае они соответствуют указателям.
Clarion
C++BYTE unsigned char
USHORT unsigned short
SHORT short
LONG long
ULONG unsigned long
SREAL float
REAL double
*CSTRING (with RAW) char&
<*CSTRING> (with RAW) char*
<*GROUP> (with RAW) void*
Отметим, что для совместимости с С++ тип возвращаемых процедурой данных не включен в составное имя. Естественным следствием этого является то, что процедуры нельзя различить по типу возвращаемого значения.
Пример:
//прототипы в C++:
#pragma name(prefix=>"")
void HADD(short,short);
void HADD(long*,unsigned char);
void HADD(short unsigned &);
void HADD(char *,void *);
!прототипы в Clarion:
MODULE('')
hADD(short,short)
HaDD(<*long>,byte)
HAdD(*ushort)
HADd(<*CSTRING>,<*GROUP>),RAW
END
Смотри также:
NAME
Директивы компилятора представляют собой операторы, которые во время компиляции предписывают ему предпринять некоторые действия. В объектный код программы, который генерирует компилятор, эти операторы не включаются, не привнося, таким образом, никаких издержек в исполняемый модуль.
ASSERT (установить правила для отладки)
ASSERT(
выражение, [сообщение] )ASSERT
Указывает правила для использования в целях отладки.выражение Булевское выражение, которое должно всегда являться истинным (любое значение, кроме пробела или ноля).
сообщение Необязательное строковое выражение (до 64K), которое отображается в диалоговом окне.
Оператор
ASSERT указывает на оценку выражения точно в той точке программы, где он помещен. Это может быть любое Булевское выражение, сформулированное таким образом, чтобы ожидаемый результат оценки всегда был истинным (любое значение, кроме пробела или ноля). Назначение ASSERT- помощь программисту при определении ошибочных присвоений.Если включен режим отладки и значение выражения – ложь (пробел или ноль), то появится сообщение об ошибке, содержащее номер строки и модуль исходного кода в точке, где заявленное выражение приняло ложное значение. Пользователь получает предложение применить к программе GPF в той точке, которая позволяет активироваться пост-мортемным отладчикам (post-mortem debuggers).
Если режим отладки отключен, то выражение всегда оценивается, но сообщение об ошибке при определении ложного результата не появляется. Чтобы активизировать сообщение об ошибке в построенном релизе (отладка выключена), в определения проекта приложения можно добавить следующее:
asserts=>on
Пример:
MyQueue QUEUE
F1 LONG
END
CODE
LOOP X# = 1 TO 10
MyQueue.F1 = X#
ADD(MyQueue)
ASSERT(~ERRORCODE(),'ADD MyQueue Error ' & ERROR())
END
LOOP X# = 1 TO 10
GET(MyQueue, X#)
ASSERT(~ERRORCODE()) !
END
!добавления
BEGIN (определить операторную структуру)
BEGIN
операторы
END
BEGIN
Объявляет структуру из операторов, рассматриваемую как единый оператор.операторы Исполняемые операторы программы.
Директива
BEGIN предписывает компилятору обрабатывать группу операторов как единую структуру. Структура BEGIN должна заканчиваться точкой или оператором END.В управляющей структуре EXECUTE директива BEGIN обычно используется для того,
чтобы несколько операторов рассматривались как один.Пример:
EXECUTE Value
Proc1 ! Выполнить, если Value=1
BEGIN
! Выполнить, если Value=2Value += 1
Proc2
END
Proc3 ! Выполнить, если Value=3
END
Смотри также:
EXECUTE
COMPILE (указать исходный текст для компиляции)
COMPILE
(терминатор[,выражение])COMPILE
Задает порцию строк исходного текста, которые должны быть включены в процесс компиляции.терминатор Строковая константа, которая отмечает последнюю строку исходного текста, подлежащего компиляции.
выражение Выражение, позволяющее осуществить условную компиляцию. Это одно из двух: выражение вида: МЕТКА СООТВЕТСТВИЯ = целочисленная константа или МЕТКА СООТВЕТСТВИЯ, чье значение ноль или единица.
Директива
COMPILE указывает блок исходного текста, который должен быть включен в процесс компиляции. Этот включаемый блок начинается с директивы COMPILE и заканчивается строкой, которая содержит строковую константу, указанную в качестве терминатора. Строка, содержащая терминатор, включается в компилируемый блок целиком.Необязательный параметр выражение обеспечивает условную компиляцию. Форма выражения фиксирована: метка соответствия или условный переключатель, установленный в системе поддержки проекта, затем знак равенства (=), за которым следует целочисленная константа.
Программный текст между директивой COMPILE и терминатором компилируется, только если выражение истинно. Если выражение содержит EQUATE, который еще не определен, то ссылочное значение EQUATE принимается равным нулю.
Хотя выражение является необязательным, директива COMPILE без этого параметра не нужна, потому, что если нет явно указанных исключений, то компилируется весь исходный текст. Директивы COMPILE и OMIT противоположны по значению друг другу.
ЛАВА
Пример:
OMIT('***',_WIDTH32_) !Пропускать, если приложение 32-битное
SIGNED EQUATE(SHORT)
UNSIGNED EQUATE(USHORT)
***
COMPILE
('***',_WIDTH32_) ! Компилировать если приложение 32-битноеSIGNED EQUATE(LONG)
UNSIGNED EQUATE(ULONG)
***
COMPILE('EndOfFile',OnceOnly = 0) !Компилировать только первый раз, потому что связанное
! с этим
OnceOnly EQUATE(1) соответствие OnceOnly определено после COMPILE
! поэтому второй проход в этой компиляции
! не будет перекомпилировать этот код
Demo EQUATE(1) ! Задается значение метки соответствия Demo
CODE
COMPILE('EndDemoChk',Demo = 1) ! Компилировать, если Demo включено
DO DemoCheck ! Проверить ограничения для демо-версии
! EndDemoChk ! Конец участка условной компиляции
! EndOfFile
!Следующий ниже пример, показывает, как OMIT и COMPILE могут быть вложены
COMPILE ('**32bit**',_width32_) !внешний COMPILE
COMPILE ('*debug*',_debug_)
DEBUGGER::BUTTONLIST Equate('&Continue|&Halt|&Debug')
!конец- COMPILE ('*debug*',_debug_
)OMIT ('*debug*',_debug_)
DEBUGGER::BUTTONLIST Equate('&Continue|&Halt')
!конец- OMIT ('*debug*',_debug_)
!конец- COMPILE ('**32bit**',_width32_) !конец внешнего COMPILE
OMIT ('**32bit**',_width32_)
DEBUGGER::BUTTONLIST Equate('&Continue|&Halt')
!конец- OMIT ('**32bit**',_width32_)
Смотри также:
OMIT, EQUATE
INCLUDE (компилировать текст другого файла)
INCLUDE(
файл [,секция]) [,ONCE]INCLUDE
Указывает что, следует компилировать исходный текст, который находится в отдельном файле, не являющемся member-модулем.файл Строковая константа, которая содержит спецификацию файла исходного текста. Если расширение опущено, то подразумевается .CLW
секция Строковая константа, которая является параметром строки директивы SECTION, помечающей текст исходного кода, который должен быть включен в текст программы.
ONCE Атрибут
ONCE предотвратит любые включения данных, которые могут вызвать предупреждения или ошибки компилятора из-за того, что компилируются неоднократно. Что касается использования атрибута секции, ONCE применим для использования файла целиком, без секций, таким образом, использование INCLUDE(файл, секция) будет проигнорировано.Директива INCLUDE задает исходный текст, который должен компилироваться, и который находится в отдельном файле, который не является MEMBER-модулем. Начиная со строки, содержащей директиву INCLUDE, указанный ею файл исходного текста или секция того файла компилируется, как если бы они находились в этом месте компилируемого исходного модуля. Вложенность вставляемых файлов может равняться 3-м, то есть можно вставить оператором INCLUDE файл, в который оператором INCLUDE вставляется файл, в который оператором INCLUDE вставляется файл, но в этот последний файл уже нельзя вставить оператором INCLUDE ничего.
Для того чтобы найти файл, компилятор использует redirection-файл (CurrentReleaseName.RED), просматривая каталоги, указанные для этого типа файлов (обычно по расширению). Это снимает необходимость указывать полный путь к включаемому в компиляцию файлу. Redirection-файл рассматривается в Руководстве программиста и главе Project System в Руководстве Программиста.
Пример:
GenLedger PROCEDURE ! Объявить процедуру
INCLUDE('filedefs.clw') ! Здесь включить объявление файлов
CODE ! Начало программной секции
INCLUDE
('Setups','ChkErr') ! Включить проверку ошибок из файла setups.claСмотри также:
SECTION, ONCE
EQUATE (назначить соответствие)
|
метка |метка
EQUATE( | [ константа ] | )|
шаблон ||
тип |EQUATE
Назначает метку другой метке или константе.метка Метка любого оператора, предшествующего оператору EQUATE. Эта форма используется для объявления альтернативной метки оператора, которая не может быть меткой процедуры или подпрограммы.
константа Числовая или строковая константа. Эта форма используется для объявления сокращенной метки для значения константы. Это позволяет легко найти и изменить константу. Она может быть опущена только в структуре ITEMIZE. Также в качестве константы может быть использовано выражение (подобно 1+2 или BOR(1111b,0001b)).
шаблон Шаблон. Эта форма используется для того, чтобы объявить сокращенную метку для шаблона. Однако форматеры экрана и отчета в редакторе Clarion не воспринимают метку соответствия, как правильный шаблон.
тип Тип данных. Обычно этот параметр используется для того, чтобы объявить единый способ объявления переменной как переменной одного из нескольких возможных типов в зависимости от установок параметров компиляции (подобно описанию typedef в С++ для простого типа данных).
Директива
EQUATE не порождает какого-нибудь выделения памяти. Она используется для того, чтобы назначить метку другой метке или константе. Метка самой директивы не может совпадать с меткой - параметром директивы.Пример:
Init EQUATE(SetUpProg)!Установить метку алиаса
Off EQUATE(0) !Off значит 0
On EQUATE(1) !On значит 1
PI EQUATE(3.1415927) !Значение Пи
EnterMsg EQUATE('Press Ctrl-Enter to SAVE')
SocSecPic EQUATE(@P###-##-####P) !Soc-sec шаблон
Смотри также
: Зарезервированные слова, ITEMIZE
ITEMIZE (перечень данных структуры)
[
метка] ITEMIZE( [ источник ] ) [,PRE( )]соответствия
END
метка
Необязательная метка для структуры ITEMIZE.ITEMIZE
Перечень данных структуры.источник
Целочисленная константа или выражение, определяющее значение для первого оператора EQUATE в структуре.PRE
Определение метку префикса для переменной в структуре.соответствия Последовательность объявлений EQUATE, которая определяет положительные целые значения в диапазоне от 0 до 65535.
Структура
ITEMIZE определяет перечень данных. Если первое соответствие не объявлено и не определено значение источника, считать его равным единице (1). Все последующие соответствия инкрементные, с шагом 1, если их величина не специфицирована. Если величина задана для подмножества соответствий, все последующие соответствия будут инкрементными с шагом, равным единице (1).На соответствия в структуре ITEMIZE можно ссылаться указанием, с добавлением спереди, префикса к метке соответствия (PRE атрибут--PRE:EquateLabel). Если же структура ITEMIZE имеет пустой префикс, тогда к соответствиям нужно обращаться с указанием метки ITEMIZE впереди метки соответствия (метка:EquateLabel). Если же префикса или метки нет, тогда на соответствия ссылаются указанием их собственной метки без префикса.
Пример
:ITEMIZE
False EQUATE(0) !False = 0
True EQUATE !True = 1
END
Color ITEMIZE(0),PRE !
Значеение источника равно нулюRed EQUATE !Color:Red = 0
White EQUATE !Color:White = 1
Blue EQUATE !Color:Blue = 2
Pink EQUATE(5) !Color:Pink = 5
Green EQUATE !Color:Green = 6
Last EQUATE
END
Stuff ITEMIZE(Color:Last + 1),PRE(My) !
Постоянное выражение как источникX EQUATE !My:X = Color:Last + 1
Y EQUATE !My:Y = Color:Last + 2
Z EQUATE !My:Z = Color:Last + 3
Смотри также:
EQUATE, PRE
OMIT (указать текст, который не должен компилироваться)
OMI
T(терминатор[,выражение])OMIT
Задает порцию строк исходного текста, которые во время компиляции должны пропускаться.терминатор Строковая константа, которая отмечает последнюю строку блока исходного текста.
выражение Выражение, позволяющее осуществить условное выполнение директивы OMIT. Выражение должно быть типа МЕТКА СООТВЕТСТВИЯ = целочисленная константа или ноль / единица или EQUATE = целое.
Директива OMIT задает блок строк исходного текста, которые должны быть пропущены при компиляции. Эти строки могут содержать комментарии к программе или часть программы, которая пропускается при тестировании. Пропускаемый блок начинается директивой OMIT и заканчивается строкой, которая содержит константу, указанную в качестве терминатора. Последняя строка целиком включается в пропускаемый блок.
Необязательный параметр выражение обеспечивает условный пропуск блока. Формат выражения фиксированный: метка соответствия или условный переключатель, установленный в системе поддержки проекта, затем знак равенства (=), за которым следует целочисленная константа.
Директива OMIT выполняется, только если выражение истинно. Таким образом, код между OMIT и терминатором компилируется только если выражение не истинно. Если выражение содержит еще не определенное EQUATE, то ссылочное значение EQUATE принимается равным нулю. COMPILE и OMIT противоположны по значению.
2 Формат исходного текста программы 77
Пример:
OMIT('**END**') ! Безусловный OMIT
! Главный цикл программы
**END**
OMIT('***',_WIDTH32_) ! OMIT если приложение 32-битное
SIGNED EQUATE(SHORT)
***
COMPILE('***',_WIDTH32_) ! COMPILE если приложение 32-битное
SIGNED EQUATE(LONG)
***
OMIT('EndOfFile',OnceOnly) ! Компилировать только первый раз, потому что связанное
! с этим
OnceOnly EQUATE(1) ! соответствие OnceOnly определено после COMPILE
! поэтому второй проход в этой компиляции
! не будет перекомпилировать этот код
Demo EQUATE(0) ! Установить значение метки Demo
CODE
OMIT('EndDemoChk',Demo = 0) ! Пропустить только если Demo выключено
DO DemoCheck ! Проверить ограничения для демо-версии
! Конец пропускаемого текста
! Конец кода
! Конец файла
! Следующий ниже пример, показывает, как OMIT и COMPILE могут быть вложены
COMPILE ('**32bit**',_width32_) !внешний COMPILE
COMPILE ('*debug*',_debug_)
DEBUGGER::BUTTONLIST Equate('&Continue|&Halt|&Debug')
!конец- COMPILE ('*debug*',_debug_)
OMIT ('*debug*',_debug_)
DEBUGGER::BUTTONLIST Equate('&Continue|&Halt')
!конец- OMIT ('*debug*',_debug_)
!конец- COMPILE ('**32bit**',_width32_) !конец внешнего COMPILE
OMIT ('**32bit**',_width32_)
DEBUGGER::BUTTONLIST Equate('&Continue|&Halt')
!конец- OMIT ('**32bit**',_width32_)
Смотри также:
COMPILE, EQUATE
ONCE (недопущение дублирования включенных данных)
Атрибут ONCE предотвращает появление предупреждений или ошибок, выдаваемых компилятором для включенных в приложение данных, компилированных больше одного раза.
Пример:
INCLUDE('KEYCODES.CLW'),ONCE
Смотри также:
INCLUDE
SECTION (указать секцию исходного текста)
SECTION
(строка)
SECTION
строка
Строковая константа, представляющая собой имя секции.Директива компилятора
SECTION идентифицирует начало блока исполняемых операторов или операторов объявления данных, которые могут быть включены в исходный текст в другом файле. Имя блока используется в качестве необязательного параметра в директиве INCLUDE для того, чтобы осуществить включение в компиляцию указанного блока исходного текста. Блок заканчивается следующей директивой SECTION или по концу файла исходного текста.Пример:
SECTION('FirstSection')
!Начало секцииFieldOne STRING(20)
FieldTwo LONG
SECTION('SecondSection')
!Конец предыдущей секции, начало новойIF Number <> SavNumber
DO GetNumber
END
SECTION('ThirdSection')
! Конец предыдущей секции, начало новойCASE Action
OF 1
DO AddRec
OF 2
DO ChgRec
OF 3
DO DelRec
END !Третья секция заканчивается по концу файла
Смотри также:
INCLUDE
|
переменная |SIZE( |
константа | )|
шаблон |SIZE
Представляет общий размер памяти, использованной для хранения.переменная Метка ранее объявленной переменной.
константа Числовая или строковая константа.
шаблон Шаблон.
Директива
SIZE предписывает компилятору подставить вместо директивы число байт памяти, используемой для хранения переменной, константы или шаблона.Пример:
SavRec STRING(1),DIM(SIZE
(Cus:Record) ! Размерность массива равна длине записиStringVar STRING(SIZE('S
oftVelocity')) ! Длина строки равна длине константыLOOP I# = 1 TO SIZE
(ParseString) ! Цикл по числу байтов в строкеPicLen = SIZE
(@P(###)###-####P) ! Запомнить длину шаблонаСмотри также:
LEN, PROP:Size, Свойства структуры файла