Как удалить круглые скобки с макросом?

Никакой запятой не разрешено в аргументе макроса, потому что это будет рассматриваться как несколько аргументов, и препроцессинг будет неправильным. Однако мы можем заключить в скобки аргумент, чтобы препроцессор рассматривал его как один аргумент. Есть ли макрос или другие методы, которые могут удалить заключенные круглые скобки?

Например, если я определяю макрос как

#define MY_MACRO(a, b)   ...

и используйте его как

MY_MACRO( A<int, double>, text );

будет неправильным. используйте его как

MY_MACRO( (A<int, double>), text)

с макросом или техникой для удаления круглых скобок будет отлично. Boost предоставляет макрос BOOST_IDENTITY_TYPE только для типов, но не для общих случаев

Ответ 1

#define ESC(...) __VA_ARGS__

затем

MY_MACRO( ESC(A<int, double>), text );

может делать то, что вы хотите.

Ответ 2

Этот макро-трюк похож на решение Якка, но устраняет необходимость явно передавать в другой макрос в качестве параметра.

#include <stdio.h>

#define _Args(...) __VA_ARGS__
#define STRIP_PARENS(X) X
#define PASS_PARAMETERS(X) STRIP_PARENS( _Args X )

int main()
{
  printf("without macro %d %d %d %d %d %d\n", (5,6,7,8,9,10) ); // This actually compiles, but it WRONG
  printf("with macro %d %d %d %d %d %d\n", PASS_PARAMETERS((5,6,7,8,9,10)) ); //Parameter "pack" enclosed in parenthesis
  return 0;
}

Конечно, вы могли бы стать творческим, сделав макрос PASS_PARAMETERS в переменный макрос и передав несколько пакетов параметров.

Ответ 3

Простым взломом может быть использование переменных массивов:

#define MY_MACRO(a, b...)   ...

Затем вы можете использовать его как:

MY_MACRO(text, A<int, double>)

Запятая во втором аргументе по-прежнему интерпретируется как разделитель аргументов (это означает, что макрос фактически вызывается с тремя аргументами), но он расширяется внутри макроса, делая поведение одинаковым. Однако переменный аргумент должен быть последним в макросе.