1

Je dois utiliser des parenthèses dans mes paramètres réels pour une macro, mais les parenthèses semblent changer le comportement de la virgule séparant les paramètres de la macro.Comment puis-je utiliser des parenthèses dans les paramètres de la macro C++?

J'ai demandé à mon préprocesseur d'exporter sa sortie dans un fichier texte, afin que je puisse voir ce qu'il produisait.
Puis j'ai effectué un test de base pour confirmer le comportement.

#define MACRO_TEST_1(X , Y) X && Y 

MACRO_TEST_1 (A , B) 
// Desired result: A && B 
// Actual result: A && B 

MACRO_TEST_1 ((C , D)) 
// Desired result: (C && D) 
// Actual result: (C , D) && 
// Warning: "not enough actual parameters for macro 'MACRO_TEST_1'" 

Il apparaît que l'addition d'une ouverture parenthese au premier paramètre, et une parenthèse fermante pour le second paramètre, provoque le préprocesseur pour traiter la virgule comme partie du premier paramètre, et suppose donc que I n'a pas fourni un deuxième paramètre du tout.
Ceci est mis en évidence par l'avertissement, ainsi que la sortie du préprocesseur ne montrant rien après le &&. Donc, ma question est, comment puis-je dire au préprocesseur que la virgule sépare les paramètres, même si les paramètres ont des parenthèses en eux?

J'ai essayé d'échapper les parenthèses ou la virgule, mais cela n'a fait aucune différence.
(Mêmes résultats, juste avec le caractère d'échappement inséré dans la sortie de préprocesseur.)

+0

Avez-vous vraiment besoin de faire cela avec des macros? Pourquoi? –

+0

@FrankPuffer Je n'entrerai pas dans les détails. C'est une situation étrange, en travaillant avec l'ancien code - probablement temporaire.Je me dis qu'il y a probablement un truc moins connu que je devrais utiliser pour obtenir des parenthèses, et c'est ce dont j'ai besoin pour le moment. – Giffyguy

+2

@FrankPuffer Les fonctions n'auraient-elles pas le même problème? 'func (1, 2)' est 2 arguments, 'func ((1, 2))' est juste un argument. – Barmar

Répondre

0

J'ai techniquement trouvé une solution, quoique moche.
Vous devez définir des symboles pour les caractères entre parenthèses.

#define OP (
#define CP) 

#define MACRO_TEST_1(X , Y) X && Y 

MACRO_TEST_1 (A , B) 
// Desired result: A && B 
// Actual result: A && B 

MACRO_TEST_1 (OP C , D CP) 
// Desired result: (C && D) 
// Actual result: (C && D) 
1

Donc ma question est, comment puis-je dire au préprocesseur que la virgule sépare les paramètres, même si les paramètres ont entre parenthèses en eux?

Je pense qu'il n'y a aucun moyen, au moins dans une telle implémentation de macros.

De l'gcc.gnu.org:

Pour appeler une macro qui prend des arguments, vous écrivez le nom de la macro suivi d'une liste d'arguments réels entre parenthèses, séparés par des virgules .

Les espaces avant et arrière dans chaque argument sont supprimés et tous les espaces entre les jetons d'un argument sont réduits à un seul espace . Les parenthèses dans chaque argument doivent être équilibrées; une virgule à l'intérieur de ces parenthèses ne met pas fin à l'argument.

Vous ne pouvez pas omettre complètement les arguments; Si une macro prend deux arguments , il doit y avoir exactement une virgule au niveau supérieur de sa liste d'arguments .

+0

Merci. Cela ressemble à une situation où un caractère d'échappement DEVRAIT raisonnablement être en mesure de changer la signification des caractères de parantheses. C'est dommage que ce ne soit pas le cas - les macros pourraient être plus larges/flexibles si échapper aux parenthèses était une possibilité. – Giffyguy

+1

@Giffyguy En tout cas les macros sont juste un héritage C qui ne peut pas être assez flexible pour de nombreuses raisons, alors ... nous avons ce que nous avons :) –