【问题标题】:Outputing backslash in a C++ macro在 C++ 宏中输出反斜杠
【发布时间】:2013-03-16 17:26:15
【问题描述】:

是否可以在 C++ 中编写宏,AFTER 扩展会输出反斜杠符号?

现在我正在使用代码:

#define SOME_ENUM(XX) \
    XX(FirstValue,) \
    XX(SecondValue,) \
    XX(SomeOtherValue,=50) \
    XX(OneMoreValue,=100) \

但是我想写一个宏,它会生成上面的代码,所以我希望能够写:

ENUM_BEGIN(name) // it should output: #define SOME_ENUM(XX) \
ENUM(ONE)        // it should output: XX(ONE,) \
//...

但我无法编写像ENUM_BEGIN 这样的宏,因为它应该扩展为末尾带有反斜杠的东西。 在 C++ 中可以吗?

【问题讨论】:

  • 如果你真的想让你的代码不可读,还有比这更简单的方法。
  • 我认为预处理器不会处理作为宏结果的预处理器指令。此外,写最后一句话让我相信这可能是糟糕的设计......
  • Jerry 我希望我的代码 可读 - 我正在尝试改进此处找到的解决方案:stackoverflow.com/questions/147267/…
  • 是否有任何 C++ 宏扩展需要以不带引号的反斜杠开头?
  • @danilo2:我并没有真正想到 意图 会产生难以理解的混乱——但我认为这几乎是不可避免的结果反正你要去哪里。 IOW,这是我的一个微妙暗示的想法,我认为你正在做的事情更有可能增加问题而不是产生真正的解决方案。

标签: c++ macros enums code-generation


【解决方案1】:

我还没有找到任何文档,但我认为你可以只做 \\ 并且你会生成一个反斜杠。

但是,在我的研究中,我发现这可能不是您必须处理的最重要的事情。正如 millsj 刚刚评论的那样,在 ENUM_BEGIN 中输出 # 时会遇到问题。见Escaping a # symbol in a #define macro?

【讨论】:

  • 你发布的链接有一个非常重要的信息:“你不能这样做。预处理器指令在宏扩展之前被识别;如果宏扩展成看起来像预处理器指令的东西,那个指令将不会被识别”所以这是不可能的。谢谢
【解决方案2】:

不,这是不可能的。与此相关的是 §2.2.1,ISO/IEC 14882:2011(E) 中描述的翻译阶段 2:

每个反斜杠字符 () 的实例后面紧跟一个换行符被删除,将物理源代码行拼接到 形成逻辑源代码行。只有任何物理上的最后一个反斜杠 源线应有资格成为此类接头的一部分。如果,如 结果,与 a 的语法匹配的字符序列 产生通用字符名称,行为未定义。一种 非空且不以换行符结尾的源文件 字符,或以紧接在前面的换行符结尾 在任何此类拼接发生之前通过反斜杠字符,应 像附加一个换行符一样被处理 文件。

基本上会发生的是\\\n(其中\n 物理上位于源中,而不是转义),将被视为\ 字符,后跟一个线拼接。剩下的\ 很可能会导致语法错误(在某些情况下它是合法的,但我目前没有看到任何情况),并且在随后的翻译阶段不会被视为线拼接(线拼接仅发生在阶段 #2)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-02-28
    • 2017-05-01
    • 2020-02-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多