繁体   English   中英

在给定命名声明的宏中使用变量声明的类型

[英]Use type of variable declaration inside macro given named declaration

我有一个大型 C++20 代码库,其中包含一堆宏实例化,这些宏实例化是这个示例的简单变体:

void main() {
  MAKE_VAR(int myInt);
  MAKE_VAR(CMyClass myClass);
  MAKE_VAR(CMyClass *pMyClass);
};

因为宏的实用程序是存在于代码实际编译之外的过程的一部分,所以#define目前是微不足道的:

#define MAKE_VAR(var) var

这意味着扩展后的结果代码很简单:

void main() {
  int myInt;
  CMyClass myClass;
  CMyClass *pMyClass;
};

但是,我正在尝试向MAKE_VAR添加更多智能,这取决于变量的类型,并且出于兼容性原因,我无法更改该宏签名(例如,让宏将类型和名称作为单独的参数)。

所以,我的问题是是否有一些咒语,我可以使用var宏参数并只生成该参数的类型,以在随后生成的代码中用作模板参数。 请注意,我不需要说出这个名字(我也不相信标准 C++20 可以做到这一点)。

也就是说,我想提出一个宏定义,以便上面的MyStruct示例扩展为类似这样的内容(需要任何额外的样板文件):

void main() {
  int myInt;
  DoThing<int>();

  CMyClass myClass;
  DoThing<CMyClass>();

  CMyClass *pMyClass;
  DoThing<CMyClass *>();
};

我的第一次尝试围绕着试图获得一些我可以传递给decltype的东西,但我找不到任何允许该名称存在的咒语。

我已经接近使用以下方法的解决方案,但我有一个不同的问题,它只能工作一次(因为FakeFunc每个实例没有唯一的名称 - 通常我会使用类似于__COUNTER__或类似的东西,但我需要它在这里跨两条线工作):

template <typename Sig> struct ArgType;
template <typename Arg> struct ArgType<void(Arg)> { using type = Arg; };

#define MAKE_VAR(var) \
  var; \
  typedef void FakeFunc( var ); \
  DoThing<typename ArgType<FakeFunc>::type>();

void main() {
  MAKE_VAR(int myInt);
  MAKE_VAR(unsigned myUInt);
};

// Macro expands to:
void main() {
  int myInt;
  typedef void FakeFunc( int myInt );
  DoThing<typename ArgType<FakeFunc>::type>();

  unsigned myUInt;
  typedef void FakeFunc( unsigned myUInt );
  DoThing<typename ArgType<FakeFunc>::type>();
};

关于完成这种方法或使用不同方法的任何想法?

编辑:现在结束问题,因为我需要澄清为什么我不能将FakeFuncDoThing放在本地 scope 中,这是我在这个简化问题中没有捕捉到的细微差别......

您无需为 function 命名:

template <typename Sig> struct ArgType;
template <typename Arg> struct ArgType<void(*)(Arg)> { using type = Arg; };

template <typename T> void DoThing() {}

#define MAKE_VAR(var) \
  var; \
  DoThing<typename ArgType<void (*)( var )>::type>();

int main() {
        MAKE_VAR(int x)
        MAKE_VAR(unsigned y)
}

现场演示

宏扩展为

int x; DoThing<typename ArgType<void (*)( int x )>::type>();
unsigned y; DoThing<typename ArgType<void (*)( unsigned y )>::type>();

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM