96

如何制作多行预处理器宏?我知道如何制作一行:

#define sqr(X) (X*X)

但我需要这样的东西:

#define someMacro(X)
    class X : public otherClass
    {
         int foo;
         void doFoo();
    };

我怎样才能让它工作?

这只是一个例子,真正的宏可能很长。

4

7 回答 7

143

\用作行继续转义字符。

#define swap(a, b) {               \
                       (a) ^= (b); \
                       (b) ^= (a); \
                       (a) ^= (b); \
                   }

编辑:正如@a​​belenky 在评论中指出的那样,该\字符必须是该行的最后一个字符。如果不是(即使之后只是空白),您将在其后的每一行上收到令人困惑的错误消息。

于 2012-05-02T18:27:51.823 回答
21

\您可以通过在每行末尾放置一个反斜杠 ( ) 来使宏跨越多行:

#define F(x) (x)   \
              *    \
             (x)
于 2012-05-02T18:29:31.433 回答
19

请注意,正如 Kerrek SB 和 coaddict 所指出的,这应该在接受的答案中指出, 总是在你的论点周围放置大括号。sqr 示例是 CompSci 课程中教授的简单示例。

问题来了:如果你按照你说“sqr(1+5)”的方式定义它会发生什么?你会得到 "1+5*1+5" 或 11
如果你正确地在它周围放置大括号,#define sqr(x) ((x)*(x))
你会得到 ((1+5) * (1+5)) 或者我们想要的 36 ...漂亮。

Ed S. 会遇到与“交换”相同的问题

于 2012-05-02T19:20:32.433 回答
6

您需要通过以下方式转义行尾的换行符\

#define sqr(X) \
        ((X)*(X))
于 2012-05-02T18:30:03.907 回答
2

尽管这不是原始问题的一部分,但其他答案都没有提到嵌入在多行宏中的注释需要仔细注意。

  • C++ 风格的注释可能不会出现在任何具有换行符的行上。
  • C 风格的注释不能跨越由换行符分隔的多行。

例子:

// WRONG:
#define someMacro(X)          \
// This comment is a problem. \
class X : public otherClass   \
{                             \
     int foo;                 \
     void doFoo();            \
};

// WRONG:
#define someMacro(X)        \
/* This comment is also     \
 * a problem. */            \
class X : public otherClass \
{                           \
     int foo;               \
     void doFoo();          \
};

// OK:
#define someMacro(X)                \
/* This comment is fine. */         \
class X : public otherClass         \
{                                   \
     int foo; /* This is OK too! */ \
     void doFoo();                  \
};
于 2021-04-03T23:39:10.770 回答
1

这是 2021 年,我们真的应该朝着 2021 年迈进inline。不正确、不必要和过度使用宏会使代码膨胀,而且它们很难调试(阅读起来很难调试)

inline void foo(x)
{
   // do whatever with x
}

但是,如果宏确实是当务之急,请do { } while(0);在这篇文章中解释为什么要在宏中使用看似毫无意义的 do-while 和 if-else 语句?

于 2021-04-04T02:56:05.643 回答
0
于 2021-04-04T02:41:30.170 回答