к оглавлению

Объявление атрибутов Clarion

Атрибуты переменных и объектов

AUTO (локальная переменная без начального значения)

AUTO

Атрибут AUTO разрешает распределение переменной, объявленной внутри процедуры, неинициализированной памяти в стеке. При распределении памяти во время выполнения программы, числовой переменной без атрибута AUTO присваивается начальное значение 0, а строковая переменная инициализируется пробелами.

Атрибут AUTO используется когда не нужно быть уверенным в нулевом или пробельном начальном значении переменной, поскольку вы намереваетесь присвоить ей некое отличное от нуля или пробелов значение. Этот атрибут экономит небольшое количество памяти во время выполнения, исключая фрагмент программного кода, необходимый для автоматической инициализации переменной.

Когда объявлен тип данных ANY вне структуры, атрибут AUTO игнорируется. Когда структура содержит ANY с атрибутом AUTO, необходимо сперва целиком очистить структуру перед тем как получать доступ к переменным типа ANY.

Пример:

SomeProc PROCEDURE

SaveCustID LONG,AUTO ! Неинициализированная локальная переменная

Смотри также: Объявление данных и распределение памяти

 

BINARY (memo-поле содержит двоичные данные)

BINARY

Атрибут BINARY (PROP:BINARY) в объявлении MEMO- или BLOB-поля указывает, что поле будет содержать данные, которые являются не только символами ASCII. Обычно этот атрибут используется для того, чтобы хранить небольшие графические изображения, предназначенные для отображения в полях типа IMAGE структуры SCREEN (или WINDOW, прим. пер). OEM конвертация неприменима в MEMO- или BLOB-полях с атрибутом BINARY. Некоторые файловые драйверы (Clarion, Btrieve, xBase) указывают, что данные в двоичном виде MEMO- и BLOB-полей – заполняются нолями, в то время как недвоичные данные – пробелами.

Пример:

Names FILE,DRIVER('Clarion'),PRE(Nam)

NbrKey KEY(Nam:Number)

Picture MEMO(48000),BINARY !двоичное MEMO - 48,000 bytes

Rec RECORD

Number SHORT

END

END

Смотри также: MEMO, BLOB, IMAGE, OEM

 

BINDABLE (переменная, используемая в динамических выражениях)

BINDABLE

Атрибут BINDABLE объявляет структуры GROUP, QUEUE, FILE и VIEW, составляющие переменные которых, можно использовать в динамических выражениях во время выполнения программы. Значение атрибута NAME каждой из переменных является логическим именем, используемым в динамических выражениях. Если атрибут NAME отсутствует, то используется имя переменной (включая префикс). Для имен всех переменных структуры в исполняемом модуле выделяется память. Таким образом, программа становится больше и использует больше памяти, чем обычно. Поэтому атрибут BINDABLE следует использовать, только если большая часть переменных структуры используется в динамических выражениях.

Форма BIND(группа) оператора BIND должна применяться в исполняемом коде перед использованием отдельных полей структуры QUEUE.

Пример:

Names QUEUE,BINDABLE ! Объявить структуру Record,

! которую можно использовать в динамических выражениях

Name STRING(20)

FileName STRING(8),NAME('FName') ! Динамическое имя: FName

Dot STRING(1) ! Динамическое имя: Dot

Extension STRING(3),NAME('EXT') ! Динамическое имя: EXT

END

CODE

BIND(Names)

Names FILE,DRIVER('Clarion'),BINDABLE

! Объявить структуру Record,

! которую можно использовать в динамических выражениях

Record RECORD

Name STRING(20)

FileName STRING(8),NAME('FName') ! Динамическое имя: FName

Dot STRING(1) ! Динамическое имя: Dot

Extension STRING(3),NAME('EXT') ! Динамическое имя: EXT

END

END

CODE

OPEN(Names)

BIND(Names)

FileNames GROUP,BINDABLE ! Объявить структуру Group,

! которую можно использовать в динамических выражениях

FileName STRING(8),NAME('FILE') ! Динамическое имя: FILE

Dot STRING('.') ! Динамическое имя: Dot

Extension STRING(3),NAME('EXT') ! Динамическое имя: EXT

END

Смотри также: BIND, UNBIND, EVALUATE

 

CREATE (разрешить создание файла)

CREATE

Атрибут CREATE (PROP:CREATE) в описании файла разрешает создание оператором CREATE дискового файла в программе, в которой этот файл объявляется. Тем самым привносятся некоторые накладные расходы, поскольку вся необходимая для этого информация должна содержаться в исполняемом модуле.

Пример:

Names FILE,DRIVER('Clarion'),CREATE ! Объявить файл, разрешить создание его

Rec RECORD

Name STRING(20)

END

END

DIM (установить размерность массива)

DIM(размерность,...,размерность)

DIM Объявить переменную-массив.

размерность Числовая константа, которая указывает число элементов в этом измерении массива.

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

Индексы уточняют, к какому элементу массива происходит обращение. Список индексов содержит индекс для каждого измерения массива. Каждый индекс отделяется запятой, а весь список заключается в квадратные скобки ([ ]). Индекс может быть представлен числовой константой, выражением или функцией. К целому массиву можно обратиться по имени без указания списка индексов.

Структура GROUP представляет собой особый случай. Каждый уровень вложенности добавляет индекс группе и переменным внутри группы. Данные, объявленные в GROUP имеют ссылки, использующие стандартный синтаксис Уточнения имени переменной с каждым индексом, указанным на том уровне GROUP, на котором он измеряется.

Пример:

Scr GROUP !Символы на экране

Row GROUP,DIM(25) !двадцать пять строк

Pos GROUP,DIM(80) !две тысячи позиций

Attr BYTE !Байт атрибутов

Char BYTE !Байт символа

END !Завершение структур GRОUР

END

END

! В приведенной выше группе:

! Scr группа из 4000 байт

! Scr.Row группа из 4000 байт

! Scr.Row[1] из 160 байт

! Scr.Row[1].Pos из 160

! Scr.Row[1].Pos[1] из 2 байт

! Scr.Row[1].Pos[1].Attr 1 байт

! Scr.Row[1].Pos[1].Char 1 байт

Month STRING(10),DIM(12) !Двенадцать месяцев

CODE

CLEAR(Month) !Очистить весь массив

Month[1] = 'January' !Присвоить значения элементам массива

Month[2] = 'February'

Month[3] = 'March'

Смотри также: MAXIMUM, Списки передаваемых параметров(передача массивов)

 

DLL (переменная определена в библиотеке .DLL)

DLL( [ флаг ] )

DLL Указывает, что переменная, FILE, QUEUE, GROUP или CLASS объявлена в библиотеке .DLL.

флаг Числовая константа, метка соответствия, или определение системы поддержки проекта, которое задает активен ли данный атрибут. Если флаг установлен в 0, то этот атрибут неактивен, как если бы его вообще не было. Если флаг имеет отличное от нуля значение, то атрибут активен.

Атрибут DLL указывает, что объявление (это могут быть структуры FILE, QUEUE, GROUP или CLASS), к которому он относится размещено в библиотеке .DLL. Объявление с атрибутом DLL должно иметь еще и атрибут EXTERNAL. Для 32-битовых приложений атрибут DLL обязателен, так как такие библиотеки являются настраиваемыми (перемещаемыми) в 32-битовом адресном пространстве, которое требует от компилятора еще одного дополнительного разыменовывания (преобразования адреса) при обращении к переменной. Атрибут DLL допустим только для переменных, объявленных вне структур FILE, QUEUE, CLASS или GRОUР.

Объявления переменных во всех библиотеках (или .EXE - модулях), которые ссылаются на общие переменные, должны быть в точности одинаковыми (с соответствующим добавлением атрибута EXTERNAL и DLL). Если объявления отличаются, то может произойти разрушение данных. Ответственность за соблюдение идентичности объявлений лежит на программисте, поскольку ни компилятор ни компоновщик не могут определить несоответствия объявлений в различных программах и библиотеках.

При использовании атрибутов EXTERNAL и DLL для объявления переменной совместно используемой .DLL и .EXE только в одной из них переменная, файл, класс или очередь должны объявляться без этих атрибутов. Во всех других библиотеках и программах следует объявлять переменную, файл, класс или очередь с атрибутами DLL и EXTERNAL. Это обеспечит уверенность в том, что для переменной, файла, класса или очереди распределена только одна область памяти и во всех библиотеках и программах при обращении к ней будут ссылки на одну и ту же область памяти, занимаемую переменной, файлом или очередью.

Можно посоветовать при разработке больших систем, использующих много библиотек DLL и/или EXE модулей, которые совместно используют одни и те же переменные, собирать реальные описания разделяемых глобальных переменных и файлов, совместно использующих все (или большинство) библиотек или исполняемых модулей, в одну библиотеку DLL. Таким образом создается одна центральная библиотека, в которой происходит отслеживание всех действительных объявлений переменных. Эта центральная библиотека связывается со всеми программами, которые используют общие переменные. Во всех других библиотеках и(или) программах в этой системе общие переменные должны объявляться с атрибутами EXTERNAL и DLL.

Флаг, используемый IDE системы поддержки проекта и генератором аппликаций:

_ABCDllMode_ Используется шаблонами ABC для всех объявлений классов, чтобы указать, что класс объявлен во внешней библиотеке .DLL. В проекте – для указания переключения в режим DLL.

Пример:

TotalCount LONG,EXTERNAL,DLL(dll_mode) ! Переменная, объявленная во внешней

!библиотеке

Cust FILE,PRE(Cus),EXTERNAL(''),DLL(1) !Файл, объявленный в модуле PROGRAM из .DLL

CustKey KEY(Cus:Name)

Record RECORD

Name STRING(20)

END

END

DLLQueue QUEUE,PRE(Que),EXTERNAL,DLL(1) ! Очередь, объявленная во внешней

!библиотеке.DLL

TotalCount LONG

END

EditEntryClass CLASS(EditClass),TYPE,MODULE('ABEIP.CLW'),LINK('ABEIP.CLW',|

_ABCLinkMode_),DLL(_ABCDllMode_)

CreateControl PROCEDURE,VIRTUAL,PROTECTED

END

Смотри также: EXTERNAL

 

DRIVER (указать тип файловой системы)

DRIVER(тип файла [,строка])

DRIVER Указывает какую файловую систему этот файл использует.

тип файла Строковая константа, содержащая имя файлового менеджера (драйвера) (Btrieve, Clarion и т.д.)

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

Атрибут DRIVER (PROP:DRIVER) указывает какой файловый драйвер используется для доступа к этому файлу данных. Это обязательный атрибут в объявлении любого файла.

Для осуществления физического доступа к файлу Clarion-программа использует файловый драйвер. Файловый драйвер действует как транслятор между Clarion-программой и файловой системой, исключая несвойственные для данной файловой системы команды. Файловые драйверы позволяют обращаться к файлам различных файловых систем, оставаясь в рамках синтаксиса языка Clarion.

Конкретный способ реализации каждой команды доступа к файлу в Clarion зависит от файлового драйвера. Из-за ограничений конкретной файловой системы некоторые команды могут быть не реализованы в драйвере. Каждый файловый драйвер описывается в Руководстве пользователя. Там перечисляются все неподдерживаемые команды доступа к файлу, атрибуты объявления файла, типы данных и/или особенности файловой системы.

Если файл объявлен без атрибута THREAD, строка драйвера (PROP:DriverString), используемая с атрибутом DRIVER, также должна быть объявлена без атрибута THREAD.

Пример:

Names FILE,DRIVER('Clarion') !Начало объявления файла

Record RECORD

Name STRING(20)

END

END

!Использование запятых для разделения нескольких строк драйвера:

A FILE,PRE(ASC),DRIVER('BASIC','/ALWAYSQUOTE=OFF,/COMMA=9,/ENDOFRECORD=1,13')

Record RECORD

Name STRING(20)

END

END

 

DUP (допускается повторение значений ключа)

DUP

Атрибут DUP (PROP:DUP) в объявлении ключа допускает наличие в файле нескольких записей с одинаковым значением ключа. Если же атрибут DUP опущен, то попытка добавить запись (или изменить данные в существующей записи) со значением ключа, уже имеющимся в файле, приведет к выдаче сообщения об ошибке “Creates Duplicate Key”, а запись в файл не запишется. Во время последовательной обработки записей с использованием последовательности ключа, записи с одинаковым значением ключа обрабатываются в том порядке, в котором они соответствуют физическому расположению в файле ключей. Операторы SET и GET обращаются к первой записи из набора имеющих одинаковый ключ. В объявлении индексов атрибут DUP не нужен, поскольку индекс всегда допускает повторение значения элементов.

Пример:

Names FILE,DRIVER('Clarion'),PRE(Nam)

NameKey KEY(Nam:Name),DUP ! Объявить ключ по полю имя, допустить совпадающие имена

NbrKey KEY(Nam:Number) ! Объявить ключ по полю номер, повтор номеров недопустим

Rec RECORD

Name STRING(20)

Number SHORT

END

END

Смотри также: KEY, GET, SET

 

ENCRYPT (шифрование файла данных)

ENCRYPT

Атрибут ENCRIPT (PROP:ENCRYPT) используется с атрибутом OWNER для того, чтобы скрыть информацию в файле данных. Этот атрибут допустим только вместе с атрибутом OWNER. Даже с помощью утилиты просмотра в шестнадцатеричном формате крайне трудно расшифровать данные в зашифрованном файле.

Пример:

Names FILE,DRIVER(‘Clarion’),OWNER(‘Clarion’),ENCRYPT

Record RECORD

Name STRING(20)

END

END

Смотри также: OWNER, EXTERNAL

 

EXTERNAL (файл объявлен во внешнем модуле)

EXTERNAL( member-модуль )

EXTERNAL Указывает, что структура FILE, QUEUE, GROUP или CLASS описывается во внешней библиотеке.

member-модуль Строковая константа (допустима только в объявлении файла, группы или очереди). Содержит имя файла (без расширения) - member-модуля, содержащего описание файла, группы или очереди без атрибута EXTERNAL. Если структура FILE, GROUP или QUEUE описывается в программном модуле или в “универсальном модуле” (т.е. оператор MEMBER для этого модуля не имеет параметра), то требуется, чтобы параметр атрибута EXTERNAL был пустой строкой или опущен.

Атрибут EXTERNAL указывает что переменная, файл, очередь, группа или класс к которому он относится, определены во внешней библиотеке. Таким образом, переменная, файл, очередь, группа или класс с атрибутом EXTERNAL объявляется и может использоваться в Clarion-программе, но память для буфера записи не выделяется. Память для буфера записи переменной, файла, очереди, группы или класса выделяется во внешней библиотеке. Этот атрибут позволяет Clarion-программе получить доступ к файлам, объявленным во внешней библиотеке как “public” - общие. Атрибут EXTERNAL недопустим в переменных, объявленных в структурах FILE, QUEUE, GROUP или CLASS.

При использовании атрибута EXTERNAL (member-модуль) для объявления файла, совместно используемого несколькими библиотеками (.LIB , .DLL и .EXE) только в одной из них этот файл должен объявляться без атрибута EXTERNAL. Во всех других библиотеках и программах следует объявлять этот файл с атрибутом EXTERNAL. Это обеспечит уверенность в том, что для него, всех библиотек и исполняемых программ распределен только один буфер записи и во всех библиотеках и программах при обращении к нему будут ссылки на одну и ту же область памяти.

Объявления файлов во всех библиотеках (или .EXE - модулях) должны быть абсолютно одинаковыми (с соответствущими добавленными атрибутами EXTERNAL и DLL). Например, объявления файла во всех библиотеках (или .EXE-модулях), которые ссылаются на эти общие файлы, должны содержать в точности одинаковые ключи, мемо и поля, объявленные точно в таком же порядке. Если объявления отличаются, то может произойти разрушение данных. Реальные последствия несовместимости объявлений файла зависят от драйвера для данной файловой системы. Ответственность за соблюдение идентичности объявлений лежит на программисте, поскольку ни компилятор не компоновщик не могут определить несоответствия объявлений в различных программах и библиотеках.

Не размещайте атрибуты OWNER, ENCRYPT или NAME в файле, который имеет атрибут EXTERNAL. Эти атрибуты могут быть размещены только в файле, не имеющего атрибут EXTERNAL, потому что этот атрибут на самом деле переобъявит файл уже объявленный в другом месте. Следовательно, эти атрибуты необязательны.

Можно посоветовать при разработке больших систем, использующих много библиотек DLL и/или EXE модулей, которые совместно используют одни и те же переменные, собирать реальные описания разделяемых глобальных переменных и файлов, совместно использующих все (или большинство) библиотек или исполняемых модулей, в одну библиотеку DLL. Таким образом, создается одна центральная DLL, в которой происходит отслеживание всех действительных объявлений переменных. Эта центральная библиотека связывается со всеми программами, которые используют общие переменные. Во всех других библиотеках и/или программах в этой системе общие переменные должны объявляться с атрибутами EXTERNAL.

Пример:

Пример:

PROGRAM

MAP

MODULE('LIB.LIB')

AddCount PROCEDURE !Внешняя библиотечная процедура

END

END

TotalCount LONG,EXTERNAL !Переменная объявлена во внешней библиотеке

!Структура файла определена в модуле PROGRAM библиотека которого включается в эту программу

Cust FILE,DRIVER('TopSpeed'),PRE(Cus),EXTERNAL('')

CustKey KEY(Cus:Name)

Record RECORD

Name STRING(20)

END

END

!Структура файла определена в MEMBER модуле библиотека которого включается в эту программу

Contact FILE,DRIVER('TopSpeed'),PRE(Con),EXTERNAL('LIB01')

ContactKey KEY(Con:Name)

Record RECORD

Name STRING(20)

END

END

!**************************************

! файл LIB.CLW содержит:

PROGRAM

MAP

MODULE('LIB01')

AddCount PROCEDURE !Библиотечная процедура

END

END

TotalCount LONG !Объявление переменной TotalCount

!Объявление файла Cust, для которого здесь же выделяется буфер записи

Cust FILE,DRIVER('TopSpeed'),PRE(Cus)

CustKey KEY(Cus:Name)

Record RECORD

Name STRING(20)

END

END

CODE

!Исполняемые операторы ...

!*************************************

! файл LIB01.CLW содержит:

MEMBER('LIB')

!Объявление файла Contact, для которого здесь же выделяется буфер записи

Contact FILE,DRIVER('TopSpeed'),PRE(Con)

ContactKey KEY(Con:Name)

Record RECORD

Name STRING(20)

END

END

AddCount PROCEDURE

CODE

TotalCount += 1

Смотри также: DLL, NAME

 

FILTER (установить ограничивающее выражение)

FILTER(выражение)

FILTER Задает выражение, используемое для оценки того, включать ли запись в виртуальный файл.

выражение Строковая константа, содержащая логическое выражение.

Атрибут FILTER (PROP:FILTER) задает выражение, используемое для оценки того, включать ли запись в виртуальный файл.

В выражении могут иметься ссылки на любые поля из структуры VIEW из структур JOIN любого уровня. Для того, чтобы запись была включена в виртуальный файл, все выражение в целом должно быть истиной. Выражение может включать любое допустимое языком Clarion логическое выражение. Во время выполнения программы выражение вычисляется (точно также как процедурой EVALUATE), поэтому все входящие в выражение переменные должны быть указаны оператором BIND.

Использование MATCH с PROP:Filter и SQL базами данных

Использование PROP:Filter как генератора SQL-фильтров для баз данных SQL теперь поддерживает функцию преобразования MATCH(s1,s2,n), передающую результат в соответствующий SQL-фильтр для всех значений n, за исключением Match:Regular. Если Вы используете режим Match:Regular, фильтр будет оцениваться на стороне клиента точно также как все другие конвертируемые фильтры не-SQL.

Другие правила преобразования:

MATCH(s1,s2,Match:Simple) будет преобразован в

s1 = s2

для всех других драйверов SQL.

MATCH(s1,s2,Match:Soundex) будет преобразован в

{fn SOUNDEX(s1)} = {fn SOUNDEX(s2)}

для всех ODBC серверов, поддерживающих функцию SOUNDEX.

MATCH(s1,s2,Match:Soundex) будет преобразован в

SOUNDEX(s1) = SOUNDEX(s2)

для Oracle Accelerator.

MATCH(s1,s2,Match:Simple + Match:NoCase) будет преобразован в

{fn UPPER(s1)} = {fn UPPER(s2)}

для всех драйверов ODBC.

MATCH(s1,s2,Match:Simple + Match:NoCase) будет преобразован в

UPPER(s1) = UPPER(s2)

для Oracle Accelerator.

MATCH(s1,s2) !Match:Wild режим

будет преобразован в

s1 LIKE %

если параметр s2 использует звездочку (*) или

s1 LIKE _

если параметр s2 использует знак вопроса (?).

Это допустимо для всех драйверов SQL.

Добавление режима Match:NoCase в режим Match:Wild преобразуется в

{fn UPPER(s1)} LIKE % или {fn UPPER(s1)} LIKE _

для всех драйверов ODBC.

Добавление режима Match:NoCase в режим Match:Wild преобразуется в

UPPER(s1) LIKE % или UPPER(s1) LIKE _

для Oracle Accelerator.

Пример:

BRW1::View:Browse VIEW(Members)

PROJECT(Mem:MemberCode,Mem:LastName,Mem:FirstName)

END

KeyValue STRING(20)

! Взять только заказы начиная с 100-го для покупателя 9999

ViewOrder VIEW(Customer),FILTER('Cus:AcctNumber = 9999 AND Hea:OrderNumber > 100')

PROJECT(Cus:AcctNumber,Cus:Name)

JOIN(Hea:AcctKey,Cus:AcctNumber) ! Соединить с файлом заголовков

PROJECT(Hea:OrderNumber)

JOIN(Dtl:OrderKey,Hea:OrderNumber) ! Соединить с файлом накладных

PROJECT(Det:Item,Det:Quantity)

JOIN(Pro:ItemKey,Dtl:Item) ! Соединить с файлом товаров

PROJECT(Pro:Description,Pro:Price)

END

END

END

END !view

CODE

BIND('KeyValue',KeyValue)

BIND(Mem:Record)

KeyValue = 'Smith'

BRW1::View:Browse{PROP:Filter} = 'Mem:LastName = KeyValue' !указать условия фильтра

OPEN(BRW1::View:Browse) !Открыть view

SET(BRW1::View:Browse) !и установить на начало

!после фильтрования и упорядочивания

CODE !

OPEN((Customer,22h); OPEN((Header,22h); OPEN((Product,22h); OPEN(Detail,22h)

BIND('Cus:AcctNumber',Cus:AcctNumber)

BIND('Hea:OrderNumber',Hea:OrderNumber)

SET(Cus:AcctKey)

OPEN(ViewOrder)

LOOP

NEXT(ViewOrder)

IF ERRORCODE() THEN BREAK.

! Обработать подошедшие записи

END

UNBIND('Cus:AcctNumber',Cus:AcctNumber)

UNBIND('Hea:AcctNumber',Hea:AcctNumber)

CLOSE(Header); CLOSE(Customer); CLOSE(Product); CLOSE(Detail)

Смотри также: BIND, UNBIND, EVALUATE, SQL

 

IMPLEMENTS(добавить методы в CLASS)

IMPLEMENTS(интерфейс)

IMPLEMENTS Добавляет дополнительные методы в класс.

интерфейс Ранее определенная структура INTERFACE, чьи методы будут определены классом, который обрабатывает указанный интерфейс.

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

У нас теперь есть поддержка для перереализации ИНТЕРФЕЙСОВ в производных классах. В новой реализации, если дочерний класс имеет атрибут IMPLEMENTS для интерфейса уже реализованного на более высоком уровне иерархии, компилятор формирует новый интерфейс VMT. Более важным является то, что если дочерний класс имеет атрибут IMPLEMENTS для интерфейса реализованного на более высоком уровне иерархии, то не все методы интерфейса могут быть переобъявлены. Смотри IMPLEMENTS Inheritance более подробно.

 

Пример 1:

MyInterface INTERFACE ! Структура интерфейса

MyProc1 PROCEDURE ! Прототип метода

MyProc2 PROCEDURE ! Прототип метода

END

MyClass CLASS,IMPLEMENTS(MyInterface) ! Класс

END

MyClass.MyInterface.MyProc1 !Объявление метода

CODE

MyClass.MyInterface.MyProc2 !Объявление метода

CODE

Пример 2:

MyInterface INTERFACE ! Структура интерфейса

MyProc1 PROCEDURE ! Прототип метода

MyProc2 PROCEDURE,BOOL ! Прототип метода

END

MyClass CLASS,IMPLEMENTS(MyInterface) ! Класс

MyProc1Worker PROCEDURE,VIRTUAL ! Прототип метода

MyProc2Worker PROCEDURE,BOOL,VIRTUAL ! Прототип метода

END

MyClass.MyProc1Worker PROCEDURE

CODE

MyClass.MyProc2Worker PROCEDURE

CODE

RETURN CHOOSE(YEAR(TODAY())>2000)

MyClass.MyInterface.MyProc1 !Объявление метода

CODE

!реализация заглушки вызывает метод класса для реальной работы:

self.MyProc1Worker

return

MyClass.MyInterface.MyProc2 !Объявление метода

CODE

!реализация заглушки вызывает метод класса для реальной работы

return self.MyProc2Worker()

MyDerivedClass CLASS(MyClass) ! ,IMPLEMENTS(MyInterface) не допустим

!интерфейс уже реализован родителем

MyProc2Worker PROCEDURE,BOOL,DERIVED

END

MyDerivedClass.MyProc2Worker PROCEDURE

BooRt BOOL

CODE

BooRt = parent.MyProc2Worker()

IF MONTH(TODAY())=1 THEN BooRt=0.

RETURN BooRt

 

Смотри также: INTERFACE, Реализация интерфейсов в производных классах

 

Реализация интерфейсов в производных классах

В версиях Clarion до 6.3, производный дочерний класс не мог иметь атрибута IMPLEMENTS для тех же интерфейсов, реализованных родительским классом. При нарушении этого правила, вызывается предупреждение компилятора о дублировании метки поля в дочернем классе и, если пользователь проигнорирует предупреждение, он/она потеряет производный дочерний класс реализаций интерфейса.

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

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

Например:

IFace INTERFACE

M1 PROCEDURE()

M2 PROCEDURE()

END

Base CLASS,TYPE,IMPLEMENTS(IFace)

X PROCEDURE()

END

Child CLASS(Base),TYPE,IMPLEMENTS(IFace)

XY PROCEDURE()

END

В версии Clarion 6.3 и выше, Virtual Memory table (VMT) указанная Base.IFace содержит указатели на функции Base.IFace.M1 и Base.IFace.M2, в то время как VMT указанная Child.IFace содержит указатели на функции Child.IFace.M1 и Child.IFace.M2.

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

В примере выше, класс Child может повторно реализовать только метод M2. Если какие-либо методы не реализованы повторно в дочернем классе, компилятор генерирует функцию "заглушки" для них, которая содержит соответствующие инструкции перехода на ближайшую реализацию, переходящую вверх по иерархии. Так, в вышеуказанном примере, если метод Child.IFace.M1 не реализован явно, компилятор для него сгенерирует код, который вызывает реализацию в родительском классе! Это огромное преимущество и гибкость в Clarion 6.3.

Пример ниже демонстрирует очень простую программу, реализующую эти понятия.

PROGRAM

MAP

END

IFace INTERFACE

MyIProc PROCEDURE

MyIProc2 PROCEDURE

MyIProc3 PROCEDURE

END

Base CLASS,IMPLEMENTS(IFace)

cMyProc PROCEDURE

END

Child CLASS(Base),IMPLEMENTS(IFace) !Допустимо только в Clarion 6.3 выше

bMyProc PROCEDURE

END

AnotherChild CLASS(Base)

IChild &IFace

END

CODE

Base.cMyProc

Child.bMyProc

Child.cMyproc !Вызов Base.cMyProc

Base.IFace.MyIProc

Child.IFace.MyIProc !комментарии:

!До C 6.3, если пользователь игнорирует сообщение "duplicate label warning", то

!произойдет вызов родительского метода base.iface.MyIProc. В C6.3 и выше, произойдет вызов

!реализации child.iface.MyIProc.

Child.IFace.MyIProc2 !Вызов Base.IFace.MyIProc2

Child.IFace.MyIProc3 !вызов Base.IFace.MyIProc3

!процедуры/методы

Base.cMyProc PROCEDURE

CODE

MESSAGE('Base.cMyProc')

Child.bMyProc PROCEDURE

CODE

MESSAGE('Child.bMyProc')

! реализации интерфейса

Base.IFace.MyIProc PROCEDURE

CODE

MESSAGE('Base.IFace.MyIProc')

Base.IFace.MyIProc2 PROCEDURE

CODE

MESSAGE('Base.IFace.MyIProc2')

Base.IFace.MyIProc3 PROCEDURE

CODE

MESSAGE('Base.IFace.MyIProc3')

Child.IFace.MyIProc PROCEDURE

CODE

MESSAGE('Child.IFace.MyIProc')

Важное замечание к примеру выше. Рассмотрим определение этого класса:

Child CLASS(Base),IMPLEMENTS(IFace)

bMyProc PROCEDURE

END

Класс Child на самом деле только реализует метод ONE из интерфейса IFace , но код вызывает все три интерфейсных метода.

 

INNER (определить операцию внутреннего присоединения)

INNER

Наличие атрибута INNER (PROP:INNER) говорит о том, что структура JOIN определяет “внутреннее присоединение” используемого по умолчанию “левого внешнего присоединения”.

По умолчанию структура VIEW строится по принципу “левое внешнее присоединение”, когда получаются все записи первичного файла VIEW-структуры независимо от того, содержит ли вторичный файл, определенный в структуре JOIN, какие-нибудь связанные записи или нет. Задание у оператора JOIN атрибута INNER приводит к тому, что из первичного файла выбираются только те записи, у которых есть по крайней мере одна связанная запись во вторичном файле. Внутреннее присоединение обычно более эффективно, нежели внешнее.

PROP:INNER это множественное свойство VIEW, указывающего наличие или отсутствие атрибута INNER в указанном JOIN. Каждый из элементов массива возвращает единицу (“1”), если JOIN имеет атрибут INNER и – пустую строку (‘’), если не имеет. Присоединения (joins) нумеруются внутри VIEW начиная с 1 в том порядке, в котором объявлены в этой структуре. (Только для чтения)

Пример:

AView VIEW(BaseFile)

JOIN(ParentFile,'BaseFile.parentID = ParentFile.ID') !JOIN 1

JOIN(GrandParent.PrimaryKey, ParentFile.GrandParentID) !JOIN 2

END

END

JOIN(OtherParent.PrimaryKey,BaseFile.OtherParentID),INNER !JOIN 3

END

END

! AView{PROP:Inner,1} возвращает ''

! AView{PROP:Inner,2} возвращает ''

! AView{PROP:Inner,3} возвращает '1'

ViewOrder VIEW(Customer),ORDER('-Hea:OrderDate,Cus:Name')

PROJECT(Cus:AcctNumber,Cus:Name,Cus:Zip)

JOIN(Hea:AcctKey,Cus:AcctNumber),INNER ! Внутреннее присоединение на файле,

!записи из которого представлены в

!Header

PROJECT(Hea:OrderNumber,Hea:OrderDate) ! отбирает только покупателей с

!заказами

JOIN(Dtl:OrderKey,Hea:OrderNumber),INNER ! Внутреннее присоединение на файле,

!записи из которого представлены в Detail

PROJECT(Det:Item,Det:Quantity) ! является естественным и более

!эффективным

JOIN(Pro:ItemKey,Dtl:Item),INNER ! Внутреннее присоединение на файле Product

PROJECT(Pro:Description,Pro:Price) ! является естественным и более

!эффективным

END

END

END

END

Смотри также: JOIN

 

LINK (точно определяет связи CLASS в проекте)

LINK( связываемый файл, [ флаг ] )

LINK Идентифицирует файл, который будет добавлен в список связей текущего проекта.

связываемый файл Строковая константа, содержащая имя файла (без расширения OBJ), связываемого с проектом. Обычно это тоже самое, что и параметр MODULE, но с уточненным именем .LIB или .OBJ файла.

флаг Численная константа, метка соответствия или определение системы проекта (Project system define), которая указывает, активен ли атрибут. Если значение этого параметра равно нулю или пропущено, то атрибут неактивен, как если бы он вообще отсутствовал. Если значение флага отличается от нуля – атрибут активен.

Атрибут LINK структуры CLASS задает имя связываемого файла, который будет добавлен в список для компиляции проекта. LINK действителен только в структуре CLASS.

Пример:

OneClass CLASS,MODULE('OneClass'),LINK('OneClass',1) ! Связь в OneClass.OBJ

LoadIt PROCEDURE

ComputeIt PROCEDURE

END

Смотри также: CLASS, MEMBER, MODULE

 

MODULE (указать модуль исходного текста для методов класса)

MODULE(исходный файл)

MODULE Указать MEMBER-модуль или файл внешней библиотеки.

исходный файл Строковая константа. Если исходный файл содержит исходный текст на языке Clarion, то эта константа содержит имя файла (без расширения), в котором находятся процедуры. Если исходный файл представляет собой внешнюю библиотеку, то эта строка должна содержать произвольный уникальный идентификатор.

Атрибут MODULE структуры CLASS указывает имя MEMBER-модуля или внешней библиотеки, в которой содержатся определение процедур для методов данного класса. Атрибут MODULE допустим только для структуры CLASS.

Пример:

OneClass CLASS,MODULE(‘OneClass’) !Определение методов находится в OneClass.CLW

LoadIt PROCEDURE !Прототип процедуры LoadIt

ComputeIt PROCEDURE !Прототип процедуры ComputeIt

END

Смотри также: CLASS, MEMBER, LINK, Прототипы процедур

 

NAME (указать внешнее имя)

NAME( [имя] )

NAME Указывает внешнее имя.

имя Строковая константа включающая внешнее имя или метку статической строковой переменной. Она может быть объявлена как глобальная, модульная или локальная переменная с атрибутом STATIC.

Атрибут NAME (PROP:NAME) задает внешнее имя переменной. Он полностью независим от атрибута EXTERNAL - между ними нет никакой связи, хотя оба эти атрибута могут использоваться с одной переменной.

Атрибут NAME может находиться в прототипе процедуры, в операторах FILE, KEY, INDEX, MEMO, в объявлении любого поля в структуре FILE, в объявлении любого поля в структуре QUEUE или в объявлении любой отдельной переменной. Этот атрибут имеет различное толкование в зависимости от того, где он применяется.

Использование в прототипах процедур

NAME может быть указан в прототипе процедуры. Константа представляет собой внешнее имя, используемое компоновщиком для того, чтобы идентифицировать процедуру или функцию из внешней библиотеки.

Использование в переменных

Атрибут NAME может использоваться для любой переменной, объявленной вне какой-либо структуры. В этом случае атрибут обеспечивает внешнее имя, используемое компоновщиком для того, чтобы идентифицировать переменную, объявленную во внешней библиотеке. Если переменная к тому же имеет атрибут EXTERNAL, то она объявляется как общая (public) переменная во внешней библиотеке с соответствующим механизмом выделения памяти. Без атрибута EXTERNAL память переменной выделяется в Clarion-программе, а сама она объявляется как внешняя переменная во внешней библиотеке.

Использование в файлах

Атрибут NAME, относящийся к объявлению файла, указывает имя файла данных для файлового драйвера. Если имя не содержит обозначения диска и каталога, то подразумеваются текущий диск и каталог. Если опущено расширение, то подразумевается используемое по умолчанию для данного файлового драйвера.

Для некоторых файловых драйверов предполагается, что ключи, индексы или MEMO поля находятся в отдельных файлах. Поэтому атрибут NAME может также употребляться в операторах KEY, INDEX или MEMO. Атрибут NAME без параметров предполагает в качестве имени метку оператора, в котором он используется (включая любой указанный префикс).

NAME может использоваться при объявлении любого поля внутри структуры RECORD (в этом случае параметр имя должен быть константой). Он обеспечивает файловый драйвер именем поля, как это, возможно, принято в файловой системе данного драйвера.

Вы можете динамически изменять имя поля внутри структуры FILE используя свойство PROP:NAME как массив. Номер элемента массива указывает порядок расположения полей внутри файла.

Атрибут NAME считается частью файловой структуры, и следует позаботиться о том, чтобы переменные, использующие отдельный исполняемый процесс и имеющие атрибут NAME, не ссылались на файлы, не использующие отдельный исполняемый процесс.

Например:

FileName STRING(255)

TFileName STRING(255),THREAD

File FILE,NAME(TFileName) ! Неправильно

File FILE,NAME(FileName) ! Правильно

File FILE,NAME(TFileName),THREAD ! Правильно

File FILE,NAME(FileName),THREAD ! Правильно

Использование в очередях

Атрибут NAME, использующийся для переменных, объявленных в структуре QUEUE, указывает внешнее имя для обработки очередей. Имя обеспечивает альтернативный метод адресации переменных в очереди, в которой используются операторы SORT, GET, PUT и ADD.

Пример:

PROGRAM

MAP

MODULE('External.Obj')

AddCount PROCEDURE(LONG),LONG,C,NAME('_AddCount') ! Функция на C именем '_AddCount'

END

END

Cust FILE,PRE(Cus),NAME(CustName) ! Имя файла в переменной CustName

CustKey KEY('Name'),NAME('c:\data\cust.idx') ! Объявить ключ cust.idx

Record RECORD

Name STRING(20) ! По умолчанию внешнее имя 'Cus:Name'

END

END

SortQue QUEUE

Field1 STRING(10),NAME('FirstField') ! Имя поля сортировки таблицы

Field2 LONG,NAME('SecondField') ! Имя поля сортировки таблицы

END

CurrentCnt LONG,EXTERNAL,NAME('Cur') ! Переменная объявлена как public во внешней

!библиотеке 'Cur'

TotalCnt LONG,NAME('Tot') ! Переменная объявлена как внешняя

! во внешней библиотеке 'Tot'

CODE

OPEN(Cust)

Cust{PROP:NAME,1} = 'Fred' !поле Cus:Name теперь называется 'Fred'

Смотри также: Прототипы процедур, QUEUE, SORT, GET, PUT, ADD, FILE, KEY, INDEX, EXTERNAL

 

NOCASE (независимость ключа или индекса от регистра букв)

NOCASE

Атрибут NOCASE (PROP:NOCASE) в объявлении ключа или индекса делает независящей от ACSII регистра букв последовательность упорядочения ключа или индекса. Все буквы в значениях ключа при записи в файл ключей преобразуются в прописные. Это преобразование не влияет на регистр букв в полях записи в файле данных. Не влияет оно и на символы, не являющиеся буквами.

Пример:

Names FILE,DRIVER('Clarion'),PRE(Nam)

NameKey KEY(Nam:Name),NOCASE ! Объявить ключ по полю имя, любой регистр букв

NbrKey KEY(Nam:Number) ! Объявить ключ по полю номер

Rec RECORD

Name STRING(20)

Number SHORT

END

END

Смотри также: INDEX, KEY

 

OEM (установить поддержку международной кодировки)

OEM

Атрибут OEM (PROP:OEM) указывает, что данный файл содержит строковые данные не на английском языке, которые были сохранены программами DOS или должны быть прочитаны в программах DOS. Эти строки автоматически перекодируются из кодировки OEM ASCII, в которой они содержатся в файле в набор символов ANSI, в котором они отображаются в Windows. Перед выводом на диск все строковые данные в записи файла автоматически перекодируются из кодировки ANSI в кодировку OEM ASCII.

Конкретный набор символов OEM ASCII, используемый при перекодировании, берется из кодовой страницы DOS, загруженной драйвером country.SYS. Это “привязывает” файл данных к конкретному языку, использующему эту кодовую страницу и значит, что эти данные нельзя использовать на компьютере, на котором загружена другая кодовая страница. Этот атрибут может поддерживаться не всеми файловыми системами. За уточнением обращайтесь к документации по конкретному файловому драйверу.

Пример:

Cust FILE,DRIVER('TopSpeed'),PRE(Cus),OEM ! Содержит не английские строки

CustKey KEY(Cus:Name)

Record RECORD

Name STRING(20)

END

END

Screen WINDOW('Window')

ENTRY(@S20),USE(Cus:Name)

BUTTON('&OK'),USE(?Ok),DEFAULT

BUTTON('&Cancel'),USE(?Cancel)

END

CODE

OPEN(Cust) ! Открыть файл Cust

SET(Cust); NEXT(Cust) ! Прочитать запись, строки в кодировке ASCII

! автоматически перекодируются в ANSI

OPEN(Screen) ! Открыть окно и вывести данные в коде ANSI

ACCEPT

CASE FIELD()

OF ?Ok

CASE EVENT()

OF EVENT:Accepted

PUT(Cust) ! Вывести запись, строки в кодировке ANSI

!автоматически перекодируются в OEM ASCII

!по загруженной в DOS кодовой странице

BREAK

END

END

END

CLOSE(Screen);CLOSE(Cust)

Смотри также: Файлы настройки среды, LOCALE

OPT (исключить нулевые значения ключа или индекса)

OPT

Атрибут OPT (PROP:OPT) позволяет исключить из индекса или ключа элементы для тех записей, в которых все поля, составляющие ключ или индекс, имеют “пустое” значение. В контексте использования этого атрибута “пустым” значением является нуль для числовых полей и заполненное пробелами (20h) строковое поле.

Пример:

Names FILE,DRIVER('Clarion'),PRE(Nam) ! Объявить структуру файла

NameKey KEY(Nam:Name),OPT !Объявить ключ по полю имя, не допуская пустых имен

NbrKey KEY(Nam:Number),OPT ! Объявить ключ по номеру, не допуская нулевых номеров

Rec RECORD

Name STRING(20)

Number SHORT

END

END

Смотри также: INDEX, KEY

 

ORDER (выражение, определяющее порядок сортировки)

ORDER(список выражений)

ORDER Задает список выражений, используемый при сортировке записей виртуального файла.

список выражений Строковая константа содержащая одно или более выражений. Каждое выражение в списке должно отделяться запятой.

Атрибут ORDER (PROP:ORDER) задает список выражений, используемый при сортировке записей виртуального файла. Выражения в списке вычисляются слева направо; приоритет сортировки убывает слева направо. Выражение, которому предшествует знак минус (-) определяет убывающую последовательность сортировки.

В выражении могут быть ссылки на любые поля структуры VIEW с любых уровней структур JOIN. Выражения в списке могут содержать в себе любые допустимые в языке Clarion выражения. Во время выполнения программы выражение вычисляется (точно так же как процедурой EVALUATE), поэтому все входящие в выражение переменные должны быть указаны оператором BIND.

8

Для систем не являющихся файловыми системами SQL, виртуальный файл использует такие ключи, хранящие один отсортированный “сегмент”, чтобы по возможности сортировались только группы записей имеющих одинаковые значения ключей. Поэтому дополнительные поля сортировки в верхней части ключа могут быть довольно эффективны.

Для SQL систем PROP:SQLOrder это только для SQL, эквивалентен PROP:ORDER. Если первым знаком выражения является знак плюс (+), то выражение присоединяется к существующему выражению порядка, что справедливо для обоих свойств. Если первым знаком выражения является минус (-), то существующее выражение присоединяется к этому выражению, что справедливо для PROP:SQLOrder. Если первый знак не является плюсом или минусом, то новое выражение заменяет собой существующее.

Пример:

! Порядок сортировки: по убыванию даты, затем по фамилии покупателя

!(в рамках каждой даты

ViewOrder VIEW(Customer),ORDER('-Hea:OrderDate,Cus:Name')

PROJECT(Cus:AcctNumber,Cus:Name,Cus:Zip)

JOIN(Hea:AcctKey,Cus:AcctNumber) ! Присоединить файл Header

PROJECT(Hea:OrderNumber,Hea:OrderDate)

JOIN(Dtl:OrderKey,Hea:OrderNumber) ! Присоединить файл Detail

PROJECT(Det:Item,Det:Quantity)

JOIN(Pro:ItemKey,Dtl:Item) ! Присоединить файл Product

PROJECT(Pro:Description,Pro:Price)

END

END

END

END

CODE

ViewOrder{PROP:ORDER} = '-Hea:OrderDate,Pro:Price-Det:DiscountPrice'

! Порядок сортировки по величине скидки внутри каждой даты

!ABC реализация примера PROP:SQLORDER

!Для списка просмотра, после открытия файлов и окна

BRW1::View:Browse{PROP:SQLOrder} = ‘Phone’

!где Phone имя столбца в базе данных SQL

!Для отчетов, после открытия файлов и окна:

Process:View{PROP:SQLOrder} = ‘au_lname’

!где au_lname столбец в базе данных SQL

Смотри также: BIND, UNBIND, EVALUATE

 

OVER (совместное использование памяти)

OVER(переменная)

OVER Допустить обращение к одной области памяти двумя различными способами.

переменная Метка переменной, которая уже занимает ту память, которая должна совместно использоваться.

Атрибут OVER позволяет к одному участку памяти адресоваться двумя различными способами. Переменная, объявленная с атрибутом OVER должна быть не больше той, поверх которой она объявляется (меньше - может быть).

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

Переменная внутри структуры GRОUР не может объявляться поверх переменной не входящей в эту структуру.

Пример:

SomeProc PROCEDURE(PassedGroup) !Процедуре передается параметр GROUP

NewGroup GROUP,OVER(PassedGroup) !Переобъявить переданный параметр GROUP

Field1 STRING(10) !Предупреждение компилятора о том, что

Field2 STRING(2) ! NewGroup не должна быть больше

END !чем PassedGroup

CustNote FILE,PRE(Csn) ! Объявить файл CustNote

Notes MEMO(2000) !мемо поле

Record RECORD

CustID LONG

END

END

CsnMemoRow STRING(10),DIM(200),OVER(Csn:Notes)

! К полю Csn:Notes можно обращаться как к целому

! или по частям по 10 байт

Смотри также: DIM

 

OWNER (объявить пароль для шифрования данных)

OWNER(пароль)

OWNER Задает пароль для шифрования данных.

пароль Строковая константа или переменная.

Атрибут OWNER (PROP:OWNER) задает пароль, который используется для шифрования данных атрибутом ENCRIPT. Если пароль не совпадает с паролем, реально использующимся в шифрованном файле, то появится ошибка “Invalid Data File”.

Использование атрибута OWNER без соответствующего атрибута ENCRYPT позволено в некоторых системах баз данных.

Если файл был объявлен без атрибута THREAD, переменная, использующая атрибут OWNER, также должна быть объявлена без атрибута THREAD.

Пример:

Customer FILE,DRIVER('Clarion'),OWNER('abCdeF'),ENCRYPT ! Зашифровать данные с помощью

!ключевого слова "abCdeF"

Record RECORD

Name STRING(20)

END

END

Смотри также: ENCRYPT, EXTERNAL

 

PRE (задать префикс)

PRE( [ префикс ] )

PRE Обеспечивает префикс для переменных в составных структурах данных.

префикс Допустимы символы букв, цифр от 0 до 9 и символ подчеркивания. Префикс должен начинаться с буквы или символа подчеркивания. Хотя префикс может быть длинным, по традиции он состоит из 1-3-х букв.

Атрибут PRE обеспечивает префикс для структур FILE, QUEUE, GROUP, REPORT или ITEMIZE. Он также допустим для объявлений типа LIKE для обеспечения отличающихся префиксов, когда LIKE объявляет копию другой составной структуры данных.

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

Для идентификации одноименных переменных, которые могут быть объявлены в структурах, не имеющих атрибута PRE, используется другой, более гибкий метод - синтаксис уточнения имен. При упоминании в исполняемых операторах, присвоениях и списках параметров к имени переменной через двоеточие спереди присоединяется имя содержащей данное поле структуры (GroupName:Label).

ЛАВА

Пример:

MasterFile FILE,DRIVER('Clarion'),PRE(Mst) ! Объявить структуру главного файла

Record RECORD

AcctNumber LONG ! ссылаться как на Mst:AcctNumber или MasterFile.AcctNumber

END

END

Detail FILE,DRIVER('Clarion'),PRE(Dtl) ! Объявить структуру файла Detail

Record RECORD

AcctNumber LONG ! ссылаться как на Dtl:AcctNumber или Detail.AcctNumber

END

END

SaveQueue QUEUE,PRE(Sav)

AcctNumber LONG !ссылаться как на Sav:AcctNumber или SaveQueue.AcctNumber

END

G1 GROUP,PRE(Mem) ! Объявить переменные в памяти

Message STRING(30) !с префиксом Mem

END

G2 LIKE(G1),PRE(Me2) !Другая GROUP как первая включающая такие же

CODE !переменные используя префикс "Me2"

IF Dtl:AcctNumber <> Mst:AcctNumber ! Это новый счет

Mem:Message = 'New Account' ! Вывести сообщение

Me2:Message = 'Variable in LIKE group'

END

IF Detail.AcctNumber <> Masterfile.AcctNumber !такое же выражение

G1.Message = 'New Account' ! Вывести сообщение

G2.Message = 'Same Variable in LIKE group'

END

Смотри также: Зарезервированные слова, Синтаксис уточнения имен

 

PRIMARY (установить первичный ключ)

PRIMARY

Атрибут PRIMARY (PROP:PRIMARY) указывает, что данный ключ является уникальным ключом содержащимся в каждой записи файла и для него недопустимы “пустые” значения любого из составляющих его полей. Это определение “по Кодду” первичного ключа в теории реляционных баз данных.

Пример:

Names FILE,DRIVER('TopSpeed'),PRE(Nam) ! Объявить структуру файла

NameKey KEY(Nam:Name),OPT ! Объявить ключ Name, пробельные значения недопустимы

NbrKey KEY(Nam:Number),PRIMARY ! Объявить файл Number как первичный ключ

Rec RECORD

Name STRING(20)

Number SHORT

END

END

Смотри также: KEY

 

PRIVATE (переменные класса доступны только в пределах модуля)

PRIVATE

Атрибут PRIVATE указывает, что переменная для которой он задан, доступна только для процедур определенных внутри исходного модуля, содержащего методы этой структуры CLASS (независимо члены класса или нет). Таким образом данные инкапсулируются от других классов.

Атрибут PRIVATE также допустим для статических (потоковых и непотоковых) переменных, объявленных вне структуры класса. Если статическая переменная объявлена с атрибутом PRIVATE, компилятор воспримет ее без общего внешнего имени. Поэтому она может быть использована только процедурами, объявленных в том же самом исходном модуле.

Пример:

OneClass CLASS,MODULE('OneClass.CLW'),TYPE

PublicVar LONG ! Объявить общую переменную

PrivateVar LONG,PRIVATE ! Объявить “публичную” переменную

BaseProc PROCEDURE(REAL Parm) ! Объявить общий метод

END

TwoClass OneClass ! Экземпляр класса OneClass

CODE

TwoClass.PublicVar = 1 ! Правильное присвоение

TwoClass.PrivateVar = 1 ! Неправильное присвоение

! Файл OneClass.CLW содержит:

MEMBER()

MAP

SomeLocalProc PROCEDURE

END

OneClass.BaseProc PROCEDURE(REAL Parm)

CODE

SELF.PrivateVar = Parm ! Правильное присвоение

SomeLocalProc PROCEDURE

CODE

TwoClass.PrivateVar = 1 ! Правильное присвоение

Смотри также: CLASS

 

PROTECTED (установить переменную частной в CLASS или порожденном CLASS)

PROTECTED

Атрибут PROTECTED указывает на то, что переменная, которой он назначен, видна только для тех PROCEDURE, которые объявлены в той же самой структуре CLASS (методах CLASS) или в любом CLASS, порожденном из того CLASS, в котором она объявлена. Это изолирует данные от любого внешнего кода для указанного класса или порожденных от него классов.

Смысл в использовании атрибута PROTECTED – обеспечить уровень инкапсуляции между общими и частными объявлениями. Все защищенные данные и методы доступны для использования внутри классов, в которых они объявлены и производных от них классах, но недоступны для внешнего от указанного класса исполняемых операторов.

Можно считать их “полуприватными”.

Пример:

OneClass CLASS,MODULE('OneClass.CLW'),TYPE

PublicVar LONG ! Объявление Общей переменной

ProtectedVar LONG,PROTECTED ! Объявление защищенной переменной

BaseProc PROCEDURE(REAL Parm) ! Объявление Общего метода

END

TwoClass OneClass ! Экземпляр OneClass

CODE

TwoClass.PublicVar = 1 ! Правильное назначение

TwoClass.ProtectedVar = 1 ! Правильное назначение, неправильно, если PRIVATE

! OneClass.CLW содержит:

MEMBER()

MAP

SomeLocalProc PROCEDURE

END

OneClass.BaseProc PROCEDURE(REAL Parm)

CODE

SELF.ProtectedVar = Parm ! Правильное назначение

SomeLocalProc PROCEDURE

CODE

TwoClass.ProtectedVar = 1 ! Правильное назначение

Смотри также: CLASS

 

RECLAIM (использовать пространство удаленных записей)

RECLAIM

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

Пример:

Names FILE,DRIVER('Clarion'),RECLAIM ! Использовать место удаленных записей

Record RECORD

Name STRING(20)

END

END

 

STATIC (статическая локальная переменная)

STATIC

Атрибут STATIC говорит о том, что переменной, группе или данных буфера очереди, объявляемой в процедуре, должна распределяться статическая память, а не память в стеке. Этот атрибут позволяет любому значению, содержащемуся в такой локальной переменной или данным буфера очереди, возобновляться при переходе от одной копии процедуры или подпрограммы к другой. Что касается структуры QUEUE, в статической памяти могут располагаться только данные ее буфера – записям очереди всегда динамически выделяется память из “кучи”.

Пример:

SomeProc PROCEDURE

SaveQueue QUEUE,STATIC !Данные буфера очереди в статической памяти

Field1 LONG !Значение сохраняется между

Field2 STRING ! ! вызовами процедур

END

AcctFile STRING(64),STATIC !STATIC нужен для использования этой

!переменной с атрибутом NAME

Transactions FILE,DRIVER('Clarion'),PRE(TRA),NAME(AcctFile)

AccountKey KEY(TRA:Account),OPT,DUP

Record RECORD

Account SHORT !Учетный код

Date LONG ! Дата транзакции

Amount DECIMAL(13,2) !Сумма сделки

END

END

Смотри также: Объявление данных и распределение памяти

 

THREAD (указать отдельный буфер расположения в памяти)

THREAD

Атрибут THREAD указывает, что переменной, файлу, группе, очереди или классу память распределяется отдельно для каждого исполняемого процесса в программе. Таким образом значение этой переменной зависит от того, какой процесс выполняется.

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

В приложениях, использующих несколько библиотек DLL, в случае если, атрибут THREAD объявлен в любой из вышеуказанных допустимых типов, любая ссылка на эти типы в связанной программе или другой DLL также должна содержать атрибут THREAD.

Использование в группах и переменных

Атрибут THREAD указывает, что статической переменной память распределяется отдельно для каждого исполняемого процесса в программе. Таким образом значение этой переменной зависит от того, какой процесс выполняется. Как только начат новый исполняемый процесс, для него создается и инициализируется пробелами или нулем новая копия этой переменной (если только не указан атрибут AUTO).

Использование в файлах

Атрибут THREAD (PROP:THREAD – допустим только для файлов) для объявлений файлов указывает, что память для буфера записи, управляющий блок файла и другие элементы структуры распределяется отдельно для каждого исполняемого процесса в программе. Таким образом значения, содержащиеся в буфере и другие элементы файла зависят от того, какой процесс выполняется. При закрытии процесса память, выделенная для буфера записи файла, управляющего блока файла и других элементов структуры файла, освобождается.

Экземпляры файлов с атрибутом THREAD считаются независимыми друг от друга. Однако файл должен открываться и закрываться для каждого нового экземпляра.

Использование в очередях

Атрибут THREAD для очереди указывает, что память для буфера статической очереди распределяется отдельно для каждого исполняемого процесса в программе. Таким образом значения, содержащиеся в буфере, зависят от того, какой процесс выполняется. Как только начат новый исполняемый процесс, для него создается новая, собственная копия очереди.

Пример:

PROGRAM

MAP

Thread1 PROCEDURE

Thread2 PROCEDURE

END

Names FILE,DRIVER('Clarion'),PRE(Nam),THREAD !Файл раздельно используемый процессами

NbrNdx INDEX(Nam:Number),OPT

Rec RECORD

Name STRING(20)

Number SHORT

END

END

GlobalVar LONG,THREAD !Копия GlobalVar в каждом из исполняемых потоков

CODE

START(Thread1)

START(Thread2)

Thread1 PROCEDURE

LocalVar LONG,THREAD !Локальная переменная отдельная для каждого процесса

!(автоматически получает атрибут STATIC)

CODE

OPEN(Names) !OPEN создает новую копию записи

SET(Names) !содержащую 1-ю запись в файле

NEXT(Names)

Thread2 PROCEDURE

SaveQueue QUEUE,THREAD !Статическая очередь, буфер которой в отдельном процессе

Name STRING(20)

Number SHORT

END

CODE

OPEN(Names) !OPEN создает другую копию буфера записи

SET(Names) !содержащую последнюю запись в файле

PREVIOUS(Names)

Смотри также: START, Объявление данных и распределение памяти, STATIC, AUTO

 

TYPE (определение типа)

TYPE

Атрибут TYPE создает для группы, очереди или класса (поименованная структура) “определение типа”. Метка поименованной структуры может быть использована как тип данных для определения других подобных групп очередей или классов (или вы можете использовать LIKE). TYPE может быть также использован для определения поименованных структур передаваемых процедурам, что позволяет принимающей процедуре напрямую обращаться к компонентам определения типа, используя синтаксис уточнения имен.

Группе, очереди или классу с атрибутом TYPE память не распределяется. Данным для класса или группы с атрибутом TYPE память также не выделяется, методы объявленные в классе должны быть определены для использования любыми последующими объектами, объявленные с таким типом. Атрибуты EXTERNAL и DLL тут неуместны.

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

Есть еще один легальный способ для адресации к компонентам переданной структуры. Объявление параметра в операторе PROCEDURE (не прототип) устанавливает локальный префикс для передаваемой очереди поскольку он указывает имя, используемое в данной процедуре, для передаваемой очереди. Например, PROCEDURE(LOC:PassedQueue) объявляет, что процедура использует для непосредственного обращения к полям-компонентам, передаваемой в качестве параметра структуры QUEUE, префикс LOC: (с именами отдельных полей, объявленными в определении типа). Однако, предпочтительнее использовать Синтаксис Уточнения именилокально прибавленные префиксы поддерживаются только для обратной совместимости.

Пример:

MAP

MyProc1 PROCEDURE(PassQue) !передаваемая очередь определена также как PassGroup

END

PassQue QUEUE,TYPE !Определение типа для передаваемой очереди

First STRING(20) !первое имя

Middle STRING(1) !средний инициал

Last STRING(20) !последнее имя

END

NameQue QUEUE(PassQue) !имя очередитакая же структура как PassQue

END !конец объявления очереди

CODE

MyProc1(NameQue) !Вызов процедуры передающей NameQue как параметр

MyProc1 PROCEDURE(PassedQue) !Процедура получает параметр QUEUE

LocalVar STRING(20)

CODE

LocalVar = PassedQue.First !присвоить NameQue.First в LocalVar из параметра

Смотри также: Уточнение имен, Списки параметров в прототипах, CLASS, GROUP

 

к оглавлению

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

НОВОСТИ ФОРУМА

Форум Рыцари теории эфира


Рыцари теории эфира
 10.11.2021 - 12:37: ПЕРСОНАЛИИ - Personalias -> WHO IS WHO - КТО ЕСТЬ КТО - Карим_Хайдаров.
10.11.2021 - 12:36: СОВЕСТЬ - Conscience -> РАСЧЕЛОВЕЧИВАНИЕ ЧЕЛОВЕКА. КОМУ ЭТО НАДО? - Карим_Хайдаров.
10.11.2021 - 12:36: ВОСПИТАНИЕ, ПРОСВЕЩЕНИЕ, ОБРАЗОВАНИЕ - Upbringing, Inlightening, Education -> Просвещение от д.м.н. Александра Алексеевича Редько - Карим_Хайдаров.
10.11.2021 - 12:35: ЭКОЛОГИЯ - Ecology -> Биологическая безопасность населения - Карим_Хайдаров.
10.11.2021 - 12:34: ВОЙНА, ПОЛИТИКА И НАУКА - War, Politics and Science -> Проблема государственного терроризма - Карим_Хайдаров.
10.11.2021 - 12:34: ВОЙНА, ПОЛИТИКА И НАУКА - War, Politics and Science -> ПРАВОСУДИЯ.НЕТ - Карим_Хайдаров.
10.11.2021 - 12:34: ВОСПИТАНИЕ, ПРОСВЕЩЕНИЕ, ОБРАЗОВАНИЕ - Upbringing, Inlightening, Education -> Просвещение от Вадима Глогера, США - Карим_Хайдаров.
10.11.2021 - 09:18: НОВЫЕ ТЕХНОЛОГИИ - New Technologies -> Волновая генетика Петра Гаряева, 5G-контроль и управление - Карим_Хайдаров.
10.11.2021 - 09:18: ЭКОЛОГИЯ - Ecology -> ЭКОЛОГИЯ ДЛЯ ВСЕХ - Карим_Хайдаров.
10.11.2021 - 09:16: ЭКОЛОГИЯ - Ecology -> ПРОБЛЕМЫ МЕДИЦИНЫ - Карим_Хайдаров.
10.11.2021 - 09:15: ВОСПИТАНИЕ, ПРОСВЕЩЕНИЕ, ОБРАЗОВАНИЕ - Upbringing, Inlightening, Education -> Просвещение от Екатерины Коваленко - Карим_Хайдаров.
10.11.2021 - 09:13: ВОСПИТАНИЕ, ПРОСВЕЩЕНИЕ, ОБРАЗОВАНИЕ - Upbringing, Inlightening, Education -> Просвещение от Вильгельма Варкентина - Карим_Хайдаров.
Bourabai Research - Технологии XXI века Bourabai Research Institution