Макросы в си - gcc
Primary tabs
Forums:
- Во-первых, ознакомьтесь с этой заметкой
- Далее ознакомьтесь с этим разделом
я рассмотрю здесь только следующий момент -
Stringification - "стротификация" - превращение в строку.
Иногда может потребоваться конвертировать макро-аргумент в строковую константу - параметры же не заменяются внутри строковых констант - но вы можете использовать решётку - # - специальный оператор препроцессора вместо параметра.
Когда макро-параметр используется вместе с на чинающей его решёткой например так -
#define log_struct(st, field, format, typecast) \ log_msg(" " #field " = " #format "\n", typecast st->field)
препроцессор заменяет его текстовым именем реально указанного в коде аргумента - конвертируя его в строковую константу.
Пример -
Вот макрос определённый в неком заголовочном файле log.h -
Для этого макроса используется способ определения , судя по всему,
допустимый только в gcc компиляторе - но всё же - эта штука в gcc называется
"stringification" - она вызывается при вызове макро-параметра (переданного в коде в макрос , определённый в виде функции)
в начале которого стоит символ "решётка " - #
вот пример макро0определения:
// macro to log fields in structs. #define log_struct(st, field, format, typecast) \ log_msg(" " #field " = " #format "\n", typecast st->field)
Например. когда мы делаем вызов вроде:
log_struct(fi, flags, 0x%08x, );
Макрос дополняется (расширяется) препроцессором до следующего вида:
log_msg(" " "flags" " = " 0x%08x" "\n", fi->flags);
Что в свою очередь эквивалентно вызову функции:
log_msg(" flags = 0x%08x\n", fi->flags);
в силу того, что в языке си производится конкатенация - сложение смежных строк.
Sometimes you may want to convert a macro argument into a string constant. Parameters are not replaced inside string constants, but you can use the `#' preprocessing operator instead. When a macro parameter is used with a leading `#', the preprocessor replaces it with the literal text of the actual argument, converted to a string constant. Unlike normal parameter replacement, the argument is not macro-expanded first. This is called stringification.
There is no way to combine an argument with surrounding text and stringify it all together. Instead, you can write a series of adjacent string constants and stringified arguments. The preprocessor will replace the stringified arguments with string constants. The C compiler will then combine all the adjacent string constants into one long string.
Here is an example of a macro definition that uses stringification:
#define WARN_IF(EXP) \ do { if (EXP) \ fprintf (stderr, "Warning: " #EXP "\n"); } \ while (0) WARN_IF (x == 0); ==> do { if (x == 0) fprintf (stderr, "Warning: " "x == 0" "\n"); } while (0);
The argument for EXP is substituted once, as-is, into the if statement, and
Пример макроса - замена макроса функционального типа на функцию =
#define log_struct(st, field, format, typecast) \ log_msg(" " #field " = " #format "\n", typecast st->field)
_____________________________________________
Источники(читать подробнее)=
http://www.codenet.ru/progr/cpp/Macros.php
http://gcc.gnu.org/onlinedocs/cpp/Macros...
Ключевые слова и фразы(для поиска)=
- Log in to post comments
- 4873 reads