【1】__pragma 与 #pragma 的区别
在C/C++标准中,#pragma是一条预处理的指令(preprocessor directive)。
简单地说,#pragma是用来向编译器传达语言标准以外的一些信息。
举个常见的例子,如果我们在代码的头文件中定义了以下语句:
#pragma once
那么,该指令会指示编译器(如果编译器支持)该头文件应该只被编译一次。
这与使用如下代码来定义头文件所达到的效果是一样的:
#ifndef THIS_HEADER #define THIS_HEADER //一些头文件的定义 #endif
在C++11中,标准定义了与预处理指令#pragma功能相同的操作符__pragma。
__pragma操作符的格式如下:
__pragma(字符串字面量)
其使用方法跟sizeof等操作符一样,将字符串字面量作为参数写在括号内即可。
那么,要达到与上例#pragma类似的效果,则只需要如下代码即可。
__pragma("once")
而相比预处理指令#pragma,由于__pragma是一个操作符,因此可以用在一些宏中。
为了加深理解,可以再看下面这个例子:
假设编译器支持4个不同程度的优化等级,如果使用#pragma,则这样写:
#pragma OPT_LEVEL n // n的范围[1, 4]
你会不会觉得每次都要重复写“#pragma...”很麻烦?如果可以利用宏定义来简化书写就好了:
#define OPT_L(x) #pragma OPT_LEVEL x
这时我们只须写:
OPT_L(3)
就相当于写:
#pragma OPT_LEVEL 3
可惜.....在C90这里永远是一个梦想!因为字符“#”在预处理指令中有特殊的用途,跟在它后面的必须是宏的参数名,例如:
#define MACRO(x) #x
那么,MACRO(example)的替换结果为:
“example”
于是可以想象,前面通过#define来定义一个关于#pragma的宏是不可行的。
不过,新的关键字“__pragma”就很好的解决了这个问题,由于__pragma并没有字符“#”,所以我们可以放心的定义宏:
#define PRAGMA(X) __pragma(#X) #define OPT_L(X) PRAGMA(OPT_LEVEL X)
这时,我们只要写:
OPT_L(2)
经过预处理后,就成为:
__pragma("OPT_LEVEL 2")
即就是:
#pragma OPT_LEVEL 2
【2】总结
该操作符__pragma 具有 与 #pragma指令相同的功能。不同之处在于:
__pragma操作符在宏定义中是以内联方式使用的。
#pragma指令不可用于宏定义中,因为编译器会将指令中的数字符号("#")解释为字符串化运算符(#)。
Good Good Study,Day Day Up.
顺序 选择 循环 总结