2012-07-27 18 views
7

Fuera de interés:Ampliación de macro y stringification: ¿Cómo se hace el nombre de la macro (no su valor) con otra macro?

#define _ACD 5, 5, 5, 30 

#define DEFAULT_NETWORK_TOKEN_KEY_CLASS _ACD 

#define DEFAULT_NETWORK_TOKEN_KEY { DEFAULT_NETWORK_TOKEN_KEY_CLASS } 

Usando DEFAULT_NETWORK_TOKEN_KEY_CLASS macro única, cómo llegar _ACD Stringified en un unsigned char const [].

const uint8 startMsg[] = ?? DEFAULT_NETWORK_TOKEN_KEY_CLASS ; 

dará como resultado _ACD solamente.

Cuál será la expansión de macro correcta para obtener _ACD aquí. En contexto de How to stringify macro having array as #define a_macro {5,7,7,97}?

+1

Creo que no es posible. Pero sé que nada es imposible. ¿Alguien? – Rick2047

Respuesta

7

(El descargo de responsabilidad estándar sobre los que no usan el preprocesador C sin una buena razón se aplica aquí).

Es ciertamente posible hacer lo que quiere hacer. Necesita una macro STRINGIFY y un poco de macro indirección.

Normalmente, STRINGIFY se define con un nivel de direccionamiento indirecto, para permitir que el preprocesador C expanda sus argumentos antes de que se sometan a una cadena. Una aplicación es:

/* The # operator converts symbol 'v' into a string */ 
#define STRINGIFY0(v) #v 
#define STRINGIFY(v) STRINGIFY0(v) 

Sin embargo, usted encontrará que esto no es suficiente:

#define _ACD 5, 5, 5, 30 
#define DEFAULT_NETWORK_TOKEN_KEY_CLASS _ACD 
#define DEFAULT_NETWORK_TOKEN_KEY { DEFAULT_NETWORK_TOKEN_KEY_CLASS } 

#define START_MSG STRINGIFY(DEFAULT_NETWORK_TOKEN_KEY_CLASS) 
const char startMsg[] = START_MSG; 

Aquí, STRINGIFY(DEFAULT_NETWORK_TOKEN_KEY_CLASS) expande a STRINGIFY0(5,5,5,30), y el preprocesador C se queja de que le has dado demasiado STRINGIFY0 muchos argumentos

La solución es retrasar la expansión de _ACD por lo que solo se expande a 5,5,5,30 cuando lo desee. Para ello, lo definen como una macro-función como:

#define _ACD() 5, 5, 5, 30 

De esta manera, _ACD solamente se ampliará cuando se "llama" que: _ACD(). DEFAULT_NETWORK_TOKEN_KEY_CLASS ahora se expandirá a _ACD, y usted tiene que expandirlo aún más "llamándolo": DEFAULT_NETWORK_TOKEN_KEY_CLASS().

El código siguiente ilustra la solución:

#include <stdio.h> 

#define STRINGIFY0(v) #v 
#define STRINGIFY(v) STRINGIFY0(v) 

#define _ACD() 5, 5, 5, 30 
#define DEFAULT_NETWORK_TOKEN_KEY_CLASS _ACD 
#define DEFAULT_NETWORK_TOKEN_KEY { DEFAULT_NETWORK_TOKEN_KEY_CLASS() } 

#define START_MSG STRINGIFY(DEFAULT_NETWORK_TOKEN_KEY_CLASS) 

const char startMsg[] = START_MSG; 

int main(int argc, char** argv) 
{ 
    printf("%s\n",startMsg); 
    return 0; 
} 
+0

Respuesta perfecta. Envía el ** _ ADC **. Aprendí mucho hoy Gracias – Rick2047