分享

#pragma

 rookie 2012-01-03

#pragma的使用最为复杂,它的作用是设定编译器的状态或者是指示编译器完成一些特定的动作。

#pragma message 在编译器中输出信息
     #pragma message(“It’s just a test”)
#pragma once 在头文件最开始处使用,保证该头文件只被编译一次
#pragma warning 在编译时,对警告(warning)进行设置

#pragma warning(disable : 34 4507) // 不显示4507和34的警告消息
#pragam warning(once : 4507)      // 4507的警告只显示一次
#pragam warning(error : 34)      // 把34号警告作为一个错误
当然,这个三个设置可以写在一起,如
#pragma warning(disable : 34 ; once : 4507 ; error : 161)

#pragma warning (push)      保存所有警告消息的现有的警告状态
#pragam warning (push,n)    保存所有警告消息的现有的警告状态, 并把全局警告等级设为n
#pragma warning (pop)       向栈中弹出最后一个警告消息,在入栈和出栈之间所作的一切改动取消
#pragma comment 将一个注释记录放入一个对象文件或执行文件中

#pragma comment(lib,"user32.lib")           //lib关键字,将user32.lib库文件放入本工程中
#pragam comment(linker,"/include:_mySymbol") //将一个链接选项放入到目标文件中。使用该指令可以强制替换开发环境中设置的链接选项
#pragma resource 把资源文件加入工程
#pragma pack 主要用于内存对齐,使用该命令可以节省内存空间

#pragma pack(n)  编译器按照n字节对齐。n=1,2,4,8,16。一般情况下,默认的n为4。
#pragma pack( )  编译器取消自定义的字节对齐方式

关于内存对齐,为了提高访问速度,在缺省情况下,编译器默认将结构,栈中的成员数据进行内存对齐。规则如下,

  1. 数据成员对齐规则:结构(struct)的数据成员,第一个数据成员放在offset为0的地方,以后每个数据成员的对齐按照#pragma pack指定的数值和这个数据成员自身长度中,比较小的那个进行。
  2. 结构的整体对齐规则:在数据成员完成各自对齐之后,结构本身也要进行对齐,对齐将按照#pragma pack指定的数值和结构最大数据成员长度中,比较小的那个进行。
  3. 结合1、2颗推断:当#pragma pack的n值等于或超过所有数据成员长度的时候,这个n值的大小将不产生任何效果。

如下结构体(默认情况,n=4),

   TestStruct demo {
       char  c1;  //长度为1<4,按照1对齐。起始位置为0,(0+0)%1 = 0,偏移为0; 存放位置是[0, 1]
       short s2;  //长度为2<4, 按照2对齐。起始位置为1,(1+1)%2 = 0,偏移为1;存放位置为[2,4]
       char  c3;  //长度为1<4, 按照1对齐。起始位置为4,(4+0)%1 = 0,偏移为0;存放位置为[4,5]
       
int   i4;  //长度为4=4, 按照4对齐。起始位置为5,(5+3)%4 = 0,偏移为3;存放位置为[8,12]
       };

因此,sizeof(demo) = 12 而不是看起来的8。改变#pragma pack(n)中的n值,可以改变内存对齐的方式,从而节省空间。当然,寻址速度上将会降低。上述的结构中,将s2和c3进行交换,sizeof(demo) = 8,所以在结构的设计中,必须考虑内存对齐。

    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多