Я пытаюсь написать что-то вроде этого:
#define COV_ON(x) \
#ifdef COVERAGE_TOOL \
_Pragma (COVERAGE #x)
#endif
Есть ли способ дать COV_ON
такое определение ? Я знаю, что то, что я сделал выше, неправильно, так как я не могу использовать #ifdef
#define. ( #
не разрешенный символ в #define
). Так есть ли решение?
c
c-preprocessor
agent.smith
источник
источник
do {} while(0)
(или эквивалент), чтобы избежать пустого оператора; см. мой ответ на связанный дубликатОтветы:
Невозможно. Сделайте наоборот:
#ifdef COVERAGE_TOOL #define COV_ON(x) _Pragma (COVERAGE #x) #else #define COV_ON(x) #endif
источник
Просто переверните его:
#ifdef COVERAGE_TOOL #define COV_ON(x) _Pragma (COVERAGE #x) #else #define COV_ON(x) /* foo */ #endif
источник
Это старый вопрос, но на него требовался актуальный ответ.
Вместо использования встроенного ifdef в макросе вы можете выборочно определить
__VA_ARGS__
макрос, который будет делать то же самое.#ifdef COVERAGE_TOOL #define IF_COVERAGE_TOOL(...) __VA_ARGS__ #else #define IF_COVERAGE_TOOL(...) #endif #define COV_ON(x) IF_COVERAGE_TOOL( _Pragma (COVERAGE #x) )
Он имеет аналогичную функциональность с ifdef, за исключением того, что вы получаете круглые скобки для разграничения начала и конца (что в большинстве IDE не имеет проблем со сворачиванием кода). Хотя вы все еще можете использовать
#define
и#ifdef
в контексте,#include
это запрещено. Чтобы получить встроенные возможности, подобные этому#else
, вы можете определить соответствующий макрос следующим образом://#define FOO #ifdef FOO #define IF_FOO(...) __VA_ARGS__ #define NO_FOO(...) #else #define IF_FOO(...) #define NO_FOO(...) __VA_ARGS__ #endif IF_FOO( #define BAR 5 int foo = BAR; ) NO_FOO( #define foo 5 )
Только один из них
NO_FOO()/IF_FOO
будет производить код.Хорошо, это удобный прием, но можем ли мы сделать его БОЛЬШЕ, чем
#ifdefs
... Булеву логику и конфигурацию? Давайте настроим несколько таблиц истинности (и пару вспомогательных макросов).#define PASTE_(x,y) x##y #define PASTE(x,y) PASTE_(x,y) #define PASTE3_(x,y,z) x##y##z #define PASTE3(x,y,z) PASTE3_(x,y,z) #define Y(...) __VA_ARGS__ #define N(...) #define IF(x) x //alternate method similar to IFNOT() #define NOT_N Y #define NOT_Y N #define IF_NOT(x) PASTE(NOT_,x) #define NOT(x) PASTE(NOT_,x) #define N_OR_N N #define N_OR_Y Y #define Y_OR_N Y #define Y_OR_Y Y #define OR(x,y) PASTE3(x,_OR_,y) #define N_AND_N N #define N_AND_Y N #define Y_AND_N N #define Y_AND_Y Y #define AND(x,y) PASTE3(x,_AND_,y) #define N_XOR_N N #define N_XOR_Y Y #define Y_XOR_N Y #define Y_XOR_Y N #define XOR(x,y) PASTE3(x,_XOR_,y) #define N_NOR_N Y #define N_NOR_Y N #define Y_NOR_N N #define Y_NOR_Y N #define NOR(x,y) PASTE3(x,_NOR_,y) #define N_NAND_N Y #define N_NAND_Y Y #define Y_NAND_N Y #define Y_NAND_Y N #define NAND(x,y) PASTE3(x,_NAND_,y) #define N_XNOR_N Y #define N_XNOR_Y N #define Y_XNOR_N N #define Y_XNOR_Y Y #define XNOR(x,y) PASTE3(x,_XNOR_,y) #define IF2(x,y,z) PASTE3(x,y,z)
config.h
#define FOO Y #define BAR N #define BAZ Y
code.c
AND(FOO,BAR)(/*do stuff if both FOO and BAR are enabled*/) IF2(FOO,_AND_,BAR)( /*do stuff if both FOO and BAR are enabled*/ ) OR(BAZ,AND(FOO,BAR))( /*do stuff if both FOO and BAR are enabled or BAZ is enabled*/ )
источник
#ifdef COVERAGE_TOOL #define COV_ON(x) _Pragma (COVERAGE #x) #else #define COV_ON(x) #endif
источник
Ты не можешь. Но вы можете поменять местами
#ifdef
и#define
:#ifdef COVERAGE_TOOL # define COV_ON(x) _Pragma (COVERAGE #x) #else # define COV_ON(x) #endif
источник
_Pragma
синтаксис; как бы вы это сделали без макроса?Как вы упомянули, невозможно использовать #ifdef в #define. Вместо этого вы должны сделать обратный порядок:
#ifdef COVERAGE_TOOL \ #define COV_ON(x) \ etc. #endif
источник