#ifdef dentro de #define

6 minutos de lectura

avatar de usuario
agente.smith

Estoy tratando de escribir algo como esto:

#define COV_ON(x) \
                #ifdef COVERAGE_TOOL \
                    _Pragma (COVERAGE #x)
                #endif

¿Hay alguna forma de definir COV_ON ¿Me gusta esto? Sé que lo que he hecho arriba está mal porque no puedo tener #ifdef dentro de #definir. (# no es un carácter permitido en #define). Entonces, ¿hay alguna solución?

  • Todas las respuestas aquí parecen omitir el uso de do {} while(0) (o equivalente) para evitar una declaración vacía; ver mi respuesta en el duplicado vinculado

    –Roger Lipscombe

    18 de abril de 2018 a las 18:13

Imposible. Hazlo al revés:

#ifdef COVERAGE_TOOL
#define COV_ON(x) _Pragma (COVERAGE #x)
#else
#define COV_ON(x)
#endif

Simplemente dale la vuelta:

#ifdef COVERAGE_TOOL
#define COV_ON(x) _Pragma (COVERAGE #x)
#else
#define COV_ON(x) /* foo */
#endif

  • Gracias por su respuesta. Intenté COV_ON (encendido) y COV_ON (apagado) pero luego aparece un error que dice error: esperado ‘)’, cerca de apagado. Cualquier idea sobre el problema.

    – agente.smith

    07/04/2011 a las 20:31


  • son cuerdas. ¿Necesito usarlos como cadenas regulares dentro de las comillas? Como “encendido” y “apagado”.

    – agente.smith

    7 abr 2011 a las 20:47

  • Depende de su definición de COBERTURA, pero supongo que necesita citarlos. Le sugiero que abra otra pregunta para este nuevo número.

    – Felipe

    7 abr 2011 a las 20:54

  • Lo probé con comillas pero no sirvió de nada. Ya he abierto un hilo nuevo. Avíseme si cree que la sintaxis de _Pragma es incorrecta.

    – agente.smith

    7 abr 2011 a las 21:07

avatar de usuario
tecnosaurio

Esta es una vieja pregunta, pero necesitaba una respuesta actualizada.

En lugar de usar un ifdef en línea dentro de la macro, puede definir selectivamente un __VA_ARGS__ macro para hacer lo mismo

#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) )

Esto tiene una funcionalidad similar a un ifdef, excepto que obtiene paréntesis para delinear el principio y el final (que la mayoría de los IDE no tienen problemas para doblar el código) Aunque aún puede usar #define y #ifdef en el contexto, #include No se permite. Para obtener capacidades en línea similares a #elsepuede definir una macro correspondiente como esta:

//#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
)

solo uno de NO_FOO()/IF_FOO producirá código.

OK, ese es un truco útil, pero ¿podemos hacerlo? MÁS útil que #ifdefs… ¿Lógica booleana y configuración quizás? Configuremos algunas tablas de verdad (y un par de macros auxiliares).

#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

código.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*/
)

  • me gusta tu estilo (=

    – étale-cohomología

    12 de julio de 2018 a las 6:34


#ifdef COVERAGE_TOOL
    #define COV_ON(x) _Pragma (COVERAGE #x)
#else
    #define COV_ON(x)
#endif

No se puede. pero puedes intercambiar #ifdef y #define:

#ifdef COVERAGE_TOOL
#   define COV_ON(x) _Pragma (COVERAGE #x)
#else
#   define COV_ON(x)
#endif

  • Gracias por su respuesta. Intenté COV_ON (encendido) y COV_ON (apagado) pero luego aparece un error que dice error: esperado ‘)’, cerca de apagado. Cualquier idea sobre el problema.

    – agente.smith

    7 abr 2011 a las 20:40

  • Sin conocer su compilador, necesitaríamos saber cuál es el esperado _Pragma la sintaxis es; ¿Cómo lo harías sin una macro?

    – sam hocevar

    7 abr 2011 a las 20:55


  • Estoy usando el compilador VC2005 y vi la sintaxis _Pragma en línea. Nunca antes usé #pragma de esta manera.

    – agente.smith

    7 abr 2011 a las 21:06

  • Necesitarás un truco de stringify, entonces. Vea esta pregunta y respuesta.

    – sam hocevar

    7 abr 2011 a las 21:10


  • Supongo que el problema es VC2005. No usan _Pragma pero usan __pragma. No estoy seguro, pero se parece a eso. Pero aún recibo una advertencia pragma desconocido con __pragma.

    – agente.smith

    7 abr 2011 a las 21:28


avatar de usuario
jberg

Como mencionó, no es posible tener un #ifdef en un #define. Lo que debe hacer en su lugar es invertir el orden:

#ifdef COVERAGE_TOOL \
  #define COV_ON(x) \
    etc.
#endif

  • Gracias por su respuesta. Intenté COV_ON (encendido) y COV_ON (apagado) pero luego aparece un error que dice error: esperado ‘)’, cerca de apagado. Cualquier idea sobre el problema.

    – agente.smith

    7 abr 2011 a las 20:40

  • Sin conocer su compilador, necesitaríamos saber cuál es el esperado _Pragma la sintaxis es; ¿Cómo lo harías sin una macro?

    – sam hocevar

    7 abr 2011 a las 20:55


  • Estoy usando el compilador VC2005 y vi la sintaxis _Pragma en línea. Nunca antes usé #pragma de esta manera.

    – agente.smith

    7 abr 2011 a las 21:06

  • Necesitarás un truco de stringify, entonces. Vea esta pregunta y respuesta.

    – sam hocevar

    7 abr 2011 a las 21:10


  • Supongo que el problema es VC2005. No usan _Pragma pero usan __pragma. No estoy seguro, pero se parece a eso. Pero aún recibo una advertencia pragma desconocido con __pragma.

    – agente.smith

    7 abr 2011 a las 21:28


¿Ha sido útil esta solución?

Esta web utiliza cookies propias y de terceros para su correcto funcionamiento y para fines analíticos y para mostrarte publicidad relacionada con sus preferencias en base a un perfil elaborado a partir de tus hábitos de navegación. Al hacer clic en el botón Aceptar, acepta el uso de estas tecnologías y el procesamiento de tus datos para estos propósitos. Configurar y más información
Privacidad