2010-02-06 15 views
5

Además de __LINE__ y __FILE__, ¿hay otras macros predefinidas útiles, como __FUNCTION_NAME__?C/C++ geniales definiciones de macro?

Si no, pero conoces otras macros útiles/útiles definidas (especialmente para propósitos de depuración), me encantaría saber sobre ellas.

Algunos han preguntado acerca de la plataforma: estoy usando gcc/g ++ en MacOSX.

+1

Eso será específico de la plataforma. ¿En que plataforma Estas tu? – dirkgently

+1

@dirkgently: '__LINE__' y' __FILE__' no son específicos de la plataforma. Y creo que hay algunas cosas más similares a las macros ('__FUNCTION_NAME__' no es una macro) que también son parte del estándar C y/o C++. – Omnifarious

+0

@Omnifarious: Sí, soy consciente de esto. Dado que, él está buscando a otros, de ahí mi pregunta. – dirkgently

Respuesta

7

puedo encontrar los siguientes (las descripciones de C99 proyecto, pero están disponibles en C89 también creo):

  • __DATE__: La fecha de la traducción de la unidad de traducción pre-procesamiento: una cadena de caracteres literal de la forma "Mmm dd aaaa", donde los nombres de los meses son los mismos que los generados por la función asctime, y el primer carácter de dd es un carácter de espacio si el valor es menor que 10. Si la fecha la traducción no está disponible, se debe suministrar una fecha válida de implementación definida .
  • __TIME__: La hora de la traducción de la unidad de procesamiento previo traducción: una cadena de caracteres literal de los "hh: mm: ss" forma que en el momento generado por la función asctime. Si el tiempo de traducción no está disponible, se debe proporcionar un tiempo válido definido por la implementación de .

Para el nombre de la función actual, C99 define __func__, pero __FUNCTION_NAME__ no es una macro estándar. Además, __func__ no es una macro, que es un identificador reservado (6.4.2.2p1):

El identificador __func__ se declarará implícitamente por el traductor como si, inmediatamente después de la llave de apertura de cada definición de función, la declaración

static const char __func__[] = "nombre-función";

apareció, donde nombre-función es el nombre de la functi que encierra léxico en.

Si está buscando algo que sea específico de la plataforma: aquí hay una lista de gcc's common predefined macros. Me gusta __COUNTER__, que es un entero secuencial único que comienza en 0. Creo que __INCLUDE_LEVEL__ también es genial, pero no estoy seguro de si puedo pensar en un uso todavía :-).

+0

'__DATE__' y' __TIME__' están disponibles también en C++. – sbi

+0

@sbi, gracias por la información. –

+0

La recursión '# include' podría finalizar con' __INCLUDE_LEVEL__'. – Potatoswatter

1

Si no me equivoco, __func__ no es una macro. Básicamente es un nombre declarado como static const char * const __func__ = "function_name"; en la parte superior de cualquier función en la que se usa. Y debe usar __func__ en lugar de cualquier cosa como __FUNCTION_NAME__ porque __func__ es parte del estándar C99.

+0

Se equivoca: la construcción C99 se llama '__func__'. –

+0

'__FUNCTION__' es una macro en MSVC. –

+0

@Chris Lutz, gracias. Creo que mi respuesta es correcta ahora. :-) – Omnifarious

2

El específico que está buscando se llama __func__, pero no es exactamente un macro, ya que su significado cambia según dónde se vea. Sin embargo, es útil y se ve como una macro.

Mi macro favorito en este momento es __STDC_VERSION__ porque me permite hacer esto:

#if !defined(__STDC_VERSION__) || __STDC_VERSION__ < 199901L 
# define inline 
# define register 
# if __GNUC__ >= 2 || _MSC_VER >= 1300 
# define __func__ __FUNCTION__ 
# else 
# define __func__ "<unknown>" 
# endif 
#endif 

Ahora puede utilizar las palabras clave C99 inline, register y __func__ para declarar las cosas sin tener que preocuparse acerca de si o no ¡el compilador que está utilizando soporta esa funcionalidad C99! En realidad, el bit para inline es más complejo ya que algunos compiladores definen __inline y otras tonterías similares, pero se entiende la idea general.

Además, se puede encontrar una lista útil de macros predefinidas para identificar compiladores, sistemas operativos y arquitecturas here.

+1

Chris, el significado de '__LINE__' también cambia dependiendo de dónde se ve, por lo que la expansión de un nombre que depende de dónde se ve en la fuente no implica necesariamente que no puede ser una macro. Tienes razón en que '__func__' no es una macro, por supuesto. –

+0

+1 para compartir el enlace de sourceforge con nosotros. – bkausbk

0

Puede obtener todas las macros predefinidas regulares de gcc como este:

$ gcc -dM -E - < /dev/null 

Por supuesto, esto no incluye macros especiales como:

__FILE__, __LINE__ and __FUNCTION__. 
0

Tiendo a hacer condiciones de una sola línea como.

#define ZZ_Slash_for_commenting_out/
#ifdef _DEBUG 
#define D_B_O std::cerr 
#else 
#define D_B_O ZZ_Slash_for_commenting_out/ 
#endif 
    D_B_O << "Your thing here" << endl; 
+0

Eso no funciona desde el estándar ANSI C de 1989. – Potatoswatter