2010-06-21 17 views
8

Supposons que je la macro suivante:Comment redéfinir une macro en utilisant la définition précédente

#define xxx(x) printf("%s\n",x); 

maintenant dans certains fichiers que je veux utiliser une version « améliorée » de cette macro sans changer son nom. La nouvelle version explore les fonctionnalités de la version originale et fait plus de travail.

#define xxx(x) do { xxx(x); yyy(x); } while(0) 

Bien sûr, me donne avertissement redefition mais pourquoi je reçois « xxx » n'a pas été déclarée dans ce cadre? Comment dois-je le définir correctement?

EDIT: selon cette http://gcc.gnu.org/onlinedocs/gcc-3.3.6/cpp/Self_002dReferential-Macros.html il devrait être possible

+1

que les macros autoréférentielles page est décrit les règles empêchant la récursion infinie du macro-remplacement. Cela ne signifie pas que vous pouvez définir une macro pour signifier plus d'une chose. –

Répondre

0

Il est pas exactement ce que vous demandez, mais il peut aider.

Vous pouvez #undef une macro avant de lui donner une nouvelle définition.

Exemple:

#ifdef xxx 
#undef xxx 
#endif 
#define xxx(x) whatever 

Je ne ai jamais entendu parler (ou vu) une macro récursive bien. Je ne pense pas que ce soit possible.

+2

Notez que le bloc '# ifdef' n'est pas nécessaire. Vous pouvez utiliser '# undef' sur un nom pour le définir comme une macro, même si ce nom n'est pas actuellement défini comme une macro. Donc, vous pouvez simplement '#undef xxx' et ensuite' #define xxx ... '. –

+0

@ James McNellis: Bon à savoir. Merci! – ereOn

6

Impossible. Les macros peuvent utiliser d'autres macros, mais elles utilisent la définition disponible lors de l'expansion, et non de la définition. Et les macros en C et C++ ne peuvent pas être récursives, donc le xxx de votre nouvelle macro n'est pas développé et est considéré comme une fonction.

3

Vous ne pourrez pas réutiliser l'ancienne définition de la macro, mais vous pouvez la définir et la redéfinir. Espérons que ce n'est pas trop compliqué à copier et à coller. Je recommande de définir une macro xxx2.

#define xxx2(x) do { xxx(x); yyy(x); } while(0); 
+3

Notez que le bloc '# ifdef' n'est pas nécessaire. Vous pouvez utiliser '# undef' sur un nom pour le définir comme une macro, même si ce nom n'est pas actuellement défini comme une macro. Donc, vous pouvez simplement '#undef xxx' et ensuite' #define xxx ... '. –

+0

Cool! Je ne savais pas à ce sujet. Laisser le '# ifdef' rend le code plus lisible. – Mike

+0

J'ai un Project-Prefix.pch où je définis les paramètres par défaut qui sont communs pour l'application de mes applications, et puis avoir des applications spécifiques Prefix.pch pour les choses qui changent. Je recevais un avertissement «Macro de problème Lexical ou Preprocesseur Redéfini» lorsque j'ai redéfini une macro et que je n'arrivais pas à comprendre comment désactiver cet avertissement dans le pré-processeur. #undef PLAY_BUTTON_TITLE puis #define PLAY_BUTTON_TITLE @ "Start" supprime l'erreur et redéfinit le bouton. – JScarry

2

Si nous connaissons le type de paramètre 'x' dans la macro 'xxx', nous pouvons redéfinir la macro en l'utilisant dans une fonction, puis définir la macro 'xxx' comme cette fonction

définition originale pour le 'xxx' macro:

#define xxx(x) printf("xxx %s\n",x); 

Dans une certaine version améliorée marque de fichier du 'xxx' macro:

/* before redefining the "xxx" macro use it in function 
* that will have enhanced version for "xxx" 
*/ 
static inline void __body_xxx(const char *x) 
{ 
    xxx(x); 
    printf("enhanced version\n"); 
} 

#undef xxx 
#define xxx(x) __body_xxx(x)