#,##
#
和 ##
操作符是和#define
宏使用的。 使用#
使在#
后的首个参数返回为一个带引号的字符串。 例如, 命令
1 |
将会使编译器把以下命令
1 | cout << to_string( Hello World! ) << endl; |
理解为
1 | cout << "Hello World!" << endl; |
使用##
连结##
前后的内容。 例如, 命令
1 |
|
将会使编译器把
1 | cout << concatenate( x, y ) << endl; |
解释为
1 | cout << xy << endl; |
理所当然,将会在标准输出处显示’10’.
#define
语法:
1 |
#define
命令用于把指定的字符串替换文件中的宏名称 。 也就是说, #define
使编译器把文件中每一个macro-name
替换为replacement-string
。 替换的字符串结束于行末。 这里是一个经典的#define
应用 (至少是在C中):
1 |
|
#define
命令的另外一个功能就是替换参数,使它假冒创建函数一样使用。如下的代码:
1 |
|
当使用复杂的宏时,最好使用额外的圆括号。 注意在以上的例子中, 变量”x
“总是出现在它自己的括号中。 这样, 它就可以在和0比较,或变成负值(乘以-1)前计算值。 同样的, 整个宏也被括号围绕, 以防止和其它代码混淆。 如果你不注意的话, 你可能会被编译器曲解你的代码。
#error
语法:
1 |
#error
命令可以简单的使编译器在发生错误时停止。 当遇到一个#error
时,编译器会自动输出行号而无论message
的内容。 本命令大多是用于调试。
#if, #ifdef, #ifndef, #else, #elif, #endif
这些命令让编译器进行简单的逻辑控制。 当一个文件被编译时, 你可以使用这些命令使某些行保留或者是去处。
1 |
如果表达式(expression)的值是”真”(true
),那么紧随该命令的代码将会被编译。
1 |
如果”macro
“已经在一个#define
声明中定义了, 那么紧随该命令的代码将会被编译。
1 |
如果”macro
“未在一个#define
声明中定义, 那么紧随命令的代码将会被编译。
一些小边注: 命令#elif
是”elseif
“的一种缩写,并且他可以想你所意愿的一样工作。 你也可以在一个#if
后插入一个”defined
“或者”!defined
“以获得更多的功能。
这里是一部分例子:
1 |
|
你应该注意到第二个例子比在你的代码中插入多个”cout
“进行调试的方法更简单。
#include
语法:
1 |
本命令包含一个文件并在当前位置插入。 两种语法的主要不同之处是在于,如果filename
括在尖括号中,那么编译器不知道如何搜索它。 如果它括在引号中, 那么编译器可以简单的搜索到文件。 两种搜索的方式是由编译器决定的,一般尖括号意味着在标准库目录中搜索, 引号就表示在当前目录中搜索。 The spiffy new 整洁的新C++ #include
目录不需要直接映射到filenames
, 至少对于标准库是这样。 这就是你有时能够成功编译以下命令的原因
1 |
#line
语法:
1 |
#line
命令是用于更改__LINE__
和 __FILE__
变量的值。 文件名是可选的。 __LINE__
和 __FILE__
变量描述被读取的当前文件和行。 命令
1 |
更改行号为10,当前文件改为”main.cpp
“。
#pragma
#pragma
命令可以让编程者让编译器执行某些事。 因为#pragma
命令的执行很特殊,不同的编译器使用有所不同。 一个选项可以跟踪程序的执行。
#undef
#undef
命令取消一个先前已定义的宏变量, 譬如一个用#define
定义的变量。
预定义变量
语法:
1 | __LINE__ |
下列参数在不同的编译器可能会有所不同, 但是一般是可用的:
__LINE__
和__FILE__
变量表示正在处理的当前行和当前文件。__DATE__
变量表示当前日期,格式为month/day/year
(月/日/年)。__TIME__
变量描述当前的时间,格式为hour:minute:second
(时:分:秒)。_cplusplus
变量只在编译一个C++程序时定义。__STDC__
变量在编译一个C程序时定义,编译C++时也有可能定义。