Форум » Clipper » Операция макроподстановки Clipper » Ответить

Операция макроподстановки Clipper

sablinsfamily: Здравствуйте, нужна информация по этой теме, любая информация. Спасибо

Ответов - 5

Dima: [pre2] & Операция макроподстановки -- унарная (Специальная) ------------------------------------------------------------------------------ Синтаксис &<макропеременная>[.] &(<макровыражение>) Операнды <макропеременная> - может быть любой символьной переменной. Точка (.) является макроразделителем и используется для маркировки конца макропеременной и отделения ее от примыкающего текста в выражении. <макровыражение> - символьное выражение, которое должно быть заключено в круглые скобки. Макроподстановка выполняется для символьной строки - результата вычисления <макровыражение>. Это позволяет компилировать и выполнить символьные строки, содержащиеся в полях баз данных и в элементах массивов. В зависимости от того, как задана макроподстановка (&), в процессе выполнения программы производится либо замещение текста, либо его компиляция. Описание Операция макроподстановки в Clipper 5.0 является специальной операцией, осуществляющей в процессе выполнения программы компиляцию выражений и текстовые подстановки в строках. Всякий раз, когда встречается операция макроподстановки, операнд передается специальному компилятору времени выполнения, который может компилировать выражения, но не операторы и команды. Текстовые подстановки В любом месте в пределах символьной строки, где встречается операция макроподстановки с именем макропеременной типа PRIVATE или PUBLIC, ее содержимое замещает эту ссылку, например: cMacro := "день" ? "Добрый &cMacro" // Результат: "Добрый день" Если в макровыражении (например, &cMacro или &(макро1+макро2)) используется LOCAL или STATIC переменная, поле базы данных или элемент массива, то результат вычисления выражения рассматривается как имя переменной, значение которой используется для подстановки. Компиляция и выполнение Если макропеременная или выражение встречается внутри выражения, то это трактуется как макровыражение, что вызывает компиляцию макропеременной или выражения и, далее, выполнение результата компиляции. В следующем примере: cMacro := "DTOC(DATE())" ? &cMacro содержимое макропеременной компилируется макрокомпилятором и затем выполняется. Код - результат компиляции - не сохраняется. Если выражение заключено в скобки и перед ним стоит операция макроподстановки (&), например: ? &(INDEXKEY(0)) сначала вычисляется выражение и уже результирующая символьная строка компилируется и выполняется как макропеременная. Одним из наиболее интересных эффектов применения макровыражений является возможность компиляции символьной строки, содержащей определение блока кода, например: dBlock := &( "{ |exp| QOUT(exp) }" ) . . . EVAL (dBlock, DATE()) В этом случае символьная строка, содержащая блок кода, компилируется и результат - блок кода - может быть сохранен в переменной и позже выполнен функцией EVAL(). Примечания ¦ Ключевые слова команд. Операция макроподстановки (&) не может быть использована для подстановки и компиляции ключевых слов команд. В Clipper 5.0 это не имеет большого значения, поскольку команды обрабатываются препроцессором во время компиляции. Переопределение ключевого слова команды может быть осуществлено либо изменением определения команды в STD.CH, либо вводом нового определения с помощью директивы #command или переопределением ключевого слова команды директивой #translate. В любом случае, переопределение ключевого слова команды осуществляется только во время компиляции, а не во время выполнения. ¦ Аргументы команд. В предыдущих версиях Clipper и в других языках макропеременные часто использовались для определения аргументов команд, передаваемых как символьные величины (в частности - аргументы команд обработки файлов и SET-команд с аргументами- переключателями). Для этих случаев в Clipper 5.0 вместо литерального аргумента используются расширенные выражения - выражения, заключенные в круглые скобки. Например, вместо xcDatabase = "Invoices" USE &xcDatabase. можно использовать xcDatabase = "Invoices" USE (xcDatabase) Особенно важны расширенные выражения в случаях использования переменных типа LOCAL и STATIC. Большинство команд преобразуется препроцессором в вызовы функций. Параметры команд, при этом, преобразуются в параметры функций. Например, в командах обработки файлов имена файлов превращаются при помощи интеллектуального преобразующего в строку маркер-результата в символьные строки и передаются в функции как аргументы. Если аргументом команды является имя или макроподстановка, то они преобразуются в символьные строки. Однако если аргумент является расширенным выражением (может быть как литералом, так и выражением с символьным типом результата), то он переписывается в конечный текст точно таким же, как он определен. Например, описание команды RENAME: #command RENAME <старое_имя> TO <новое_имя> =>; FRENAME(<(старое_имя)>,<(новое_имя)>) // RENAME &старое_имя TO &новое_имя RENAME (старое_имя) TO (новое_имя) После работы препроцессора в конечный текст будет записано: FRENAME("&старое_имя","&новое_имя") FRENAME(старое_имя, новое_имя) При обработке препроцессором, имена макропеременных переносятся в результирующий текст, заключенными в апострофы, и не компилируются. Во время выполнения производится текстовая подстановка, и их значения передаются как параметры в функцию FRENAME(). Это относится только к PUBLIC и PRIVATE и не относится к LOCAL и STATIC макропеременным, поскольку имена последних не доступны во время выполнения. Более подробную информацию о различиях между переменными LOCAL и STATIC, PRIVATE и PUBLIC вы найдете в разделе "Переменные". ¦ Списки как аргументы команд. Операция макроподстановки (&) не может полностью заместить или откомпилировать список, используемый в качестве аргумента во многих командах. Особенно это относится к тем командам, в которых список аргументов препроцессор преобразует в массив и блок кода. Примером могут служить аргументы предложения FIELDS и команды SET INDEX, а исключением является команда SET COLOR, в которой список цветов препроцессор преобразует в одну символьную строку и передает их функции SETCOLOR(). В любом случае параметры в списке параметров должны быть определены как расширенные выражения (в скобках), и каждый параметр в списке должен быть заранее определен: LOCAL xcIndex := {"Ntx1", "Ntx2"} SET INDEX TO (xcIndex[1]), (xcIndex[2]) ¦ Массивы. Операция макроподстановки (&) может быть использована в комбинации как с массивами, так и с отдельными их элементами. Однако в силу того, что возможности массивов в Clipper 5.0 расширены, уменьшается необходимость в использовании операции макроподстановки для ссылки на элементы массивов. Становится возможным присваивать ссылки на массивы переменным, возвращать ссылки на массивы из функций пользователя, включать ссылки на массивы в другие массивы. Кроме того, массивы могут быть созданы присвоением литерального выражения или при помощи функции ARRAY(). За дополнительной информацией о массивах следует обращаться к разделу "Массивы" в книге "Справочник". Как макропеременные, так и макровыражения могут использоваться для указания массивов или их элементов, однако, их нельзя использовать для объявления размерности индексов в операторах описаний PRIVATE или PUBLIC. Кроме того, операция макроподстановки (&) не может использоваться в операторах описания LOCAL или STATIC. Это вызовет ошибку компиляции. Следующий пример демонстрирует использование макропеременных при доступе к элементам массива: cName := "aArray" nElements := 5 cNameElement := "aArray[1]" // PRIVATE &cName.[nElements] // создает массив aArray с 5 элементами &cNameElement. := 100 // присваивает 1 элементу значение 100 &cName.[3] := "abc" // присваивает 3 элементу значение "abc" Операция макроподстановки (&) может быть успешно применена к элементу массива, если ссылка производится с использованием макровыражения. Использование же элемента массива в качестве макропеременной, вызовет формирование ошибки времени выполнения. В следующем примере выводится содержимое всех полей текущей записи базы данных: USE Customer NEW aStruc := DBSTRUCT() // FOR nField := 1 TO LEN(aStruc) ? &(aStruc[nField, 1]) NEXT ¦ Блоки кода. В большинстве случаев операция макроподстановки может использоваться с макропеременной или макровыражением в блоке кода. Однако есть ограничение, когда макропеременная или макровыражение содержат описанную ранее переменную. Это ограничение относится к случаю, когда комбинированное выражение (выражение, которое содержит операцию и один или более операндов) включает используемую внутри блока кода операцию макроподстановки (&). В этом случае происходит формирование ошибки времени выполнения. Следует отметить, что это ограничение имеет важное значение при использовании переменных LOCAL и STATIC в предложениях условий команд, поскольку они преобразуются в блоки кода в процессе работы препроцессора. Это относится к предложениям FOR и WHILE, к команде SET FILTER и к команде установления связи SET RELATION. Наиболее распространенный способ обойти это ограничение - собрать все выражения в одну макропеременную и потом связать с ней операцию макроподстановки. ¦ Макроусловия. Когда операция макроподстановки (&) используется в предложениях условий для команд баз данных, таких как FOR или WHILE, существует несколько ограничений, связанных со сложностью и размером выражений:  Максимальный размер строки, которую может обрабатывать макрокомпилятор, составляет 254 символа.  Существует предел сложности условий (чем они сложнее, тем меньше условий можно задавать). ¦ Процедуры и функции. Вызовы процедур и функций могут осуществляться с использованием макропеременных и выражений. Макропеременная может содержать все или только часть имени процедуры, вызываемой оператором DO. При вызове функции (встроенной или определенной пользователем) макропеременная должна содержать как имя функции, так и все ее параметры. Использование блоков кода в Clipper 5.0 позволяет снять эти ограничения. Все вызовы процедур и функций с использованием операции макроподстановки могут быть заменены использованием блоков кода. Например, следующий фрагмент программы: cProc := "AcctsRpt()" . . . DO &cProc может быть заменен на: bProc := &( "{ || AcctsRpt() }" ) . . . EVAL(bProc) Наиболее очевидным преимуществом использования блоков кода вместо макроподстановок является то, что результат компиляции строки, содержащей блок кода, может быть сохранен и, таким образом, блок кода должен компилироваться только один раз. Компиляция же макроподстановки выполняется каждый раз заново. ¦ Внешние ссылки. Процедуры и функции пользователя, указываемые только в макровыражениях и макропеременных, должны быть описаны как EXTERNAL, иначе компоновщик не включит их в выполняемый (.EXE) файл. Исключение составляет случай, когда процедура или функция пользователя была включена в предварительно скомпонованную (.PLL) библиотеку. ¦ TEXT...ENDTEXT. Для макропеременных внутри этой конструкции производится текстовая подстановка. Помните, что имена полей баз данных не могут использоваться в качестве макропеременных для текстовой подстановки. Для разрешения этой проблемы следует предварительно присвоить содержимое поля переменной, используемой в макроподстановке. Например: USE Customer NEW myVar := Customer->CustName TEXT Это текст с макроподстановкой &myVar ENDTEXT ¦ Вложенные макроопределения. Clipper допускает вложенные макроопределения. Например, после присвоения одной макропеременной имени другой макропеременной, макроподстановка второй может быть использована при макроподстановке первой. Например: cOne = "&cTwo" cTwo = "cThree" cThree = "hello" // ? &cOne // Результат: "hello" [/pre2]

sablinsfamily: Dima пишет: Спасибо огромное, может ещё какие иллюстрации есть? Поможет все!

PSP: sablinsfamily пишет: может ещё какие иллюстрации есть? Поможет все! Того, что Дима дал, вполне достаточно.


Dima: sablinsfamily Если что не понятно , спрашивай. Поможем.

sablinsfamily: PSP пишет: Того, что Дима дал, вполне достаточно. Dima пишет: Если что не понятно , спрашивай. Поможем. Хорошо, спасибо.



полная версия страницы