C++宏

系统自带的几个比较有用的宏

__TIME__ 系统当前时间,表示方式为H:M:S

__FILE__ 文件名

__DATE__ 日期

__LINE__ 到LINE为止文件代码行数

带参数的宏----》》》宏函数

宏的作用就是全部替换

#include<iostream>

#define SWAP(T, m, n) {T t=m;m=n;n=t;};
int main()
{
    using namespace std;
    int a = 10, b = 20;
    double c = 12.3, d = 45.6;
    SWAP(int, a, b)
    SWAP(int, c, d)
    cout << a << "  " << b << endl;
    cout << c << "  " << d << endl;

    system("pause");
    return 0;
}

下面给出预编译后的代码

#include<iostream>

#define SWAP(T, m, n) {T t=m;m=n;n=t;};
int main()
{
    using namespace std;
    int a = 10, b = 20;
    double c = 12.3, d = 45.6;
    {int t = b; b = a; a = t; };
    {int t = d; d = c; c = t; };
    cout << a << "  " << b << endl;
    cout << c << "  " << d << endl;

    system("pause");
    return 0;
}

这里可以很明显的看到全部替换的含义,就是一字不漏的替换,千万不要以为这里是像函数传实参传入拷贝副本

只是把宏定义的代码原封不动的搬到对应的代码行

带参数宏的几个问题

1:参数尽量括起来

#include<iostream>

#define SWAP(T, m, n) {T t=m;m=n;n=t;};
#define PI 3.14159
#define AREA(r) PI*r*r      //PI*(r)*(r)可以获得我们想要的结果,所以宏中定义的参数一般都要用括号括起来
int main()
{
    using namespace std;
    int a = 10, b = 20;
    double c = 12.3, d = 45.6;

    cout << AREA(a) << endl;   //输出结果314.159
    cout << AREA(a+b) << endl;  //传入的是表达式,输出结果215.416
    cout << PI*a + b*a + b;   //输出结果215.416 替换后,并没有按照预期的结果,运算符的优先级使得我们的结果发生了变化
    system("pause");
    return 0;
}

2:表达式尽量括起来

#include<iostream>

#define SWAP(T, m, n) {T t=m;m=n;n=t;};
#define PI 3.14159
#define AREA(r) PI*r*r
#define MAX(x,y) x>y?x:y //用括号括起来(x>y?x:y)这样就可以得到我们想要的结果
int main()//我这里想返回两个最大值的和,结果却返回的是50,
{
    using namespace std;
    int a = 10, b = 20, e = 50, f = 60;
    double c = 12.3, d = 45.6;

    cout << (MAX(a, b)+MAX(e,f)); //预处理后的结果是x>y?x:y+x>y?x:y;不是我们需要的结果,处理办法是在宏定义出

    system("pause");
    return 0;
}

宏还有很多其他问题,比如对++运算符,但是只要记住,宏所做的操作全部都是原始替换,将相应的字符替换进去就可以发现错误出在哪里

宏中另外两个特殊字符的用法

# ,将参数转化为字符串 比如str(hello),我输入的只是hello,但是我在宏中定义str(r) #r,那么r就转为字符串,可以顺利输出。

##, 拼接标示符

#include<iostream>

#define SWAP(T, m, n) {T t=m;m=n;n=t;};
#define PI 3.14159
#define AREA(r) PI*r*r
#define MAX(x,y) x>y?x:y
#define welcome(who) welcome##who()
    using namespace std;
    void welcomeAA(){ cout << "A" << endl; };
    void welcomeBB(){ cout << "B" << endl; };
int main()
{
    welcome(AA);
    system("pause");
    return 0;
}

C++宏,布布扣,bubuko.com

时间: 2024-11-08 22:10:38

C++宏的相关文章

宏定义中的#,##,...,do{}while(0),__VA_ARGS__

宏定义中的#,## 1.在一个预处理器宏中的参数前面使用一个#,预处理器会把这个参数转换为一个字符数组 #define syslog(a) fprintf(stderr,"Warning: " #a"\n"); 2.简单的说,"## "是一种分隔连接方式,它的作用是先分隔,然后进行强制连接 举列 -- 试比较下述几个宏定义的区别 #define A1(name, type)  type name_##type##_type 或 #define A

Word中 简单宏的使用

 (注意:打开文档时按住 Shift 键可以阻止 AutoOpen 宏运行) 1:Word中能够自动运行的默认宏代码名称及触发条件如下 -------------------------------------------------------- 1.名称:AutoExec 条件:启动Word或加载全局模板 2.名称:AutoNew 条件:每次生成新文档时 3.名称:AutoOpen 条件:每次打开一个已有文档时 4.名称:AutoClose 条件:每次关闭文档时 5.名称:AutoExit

常用的预定义的宏

常用的预定义的宏 常用的预定义的宏有:__LINE__ 当前源程序行的行号,用十进制整数常量表示 __FILE__ 当前源文件的名称,用字符串常量表示 __DATE__ 编译时的日期,用"MM dd yyyy"形式的字符串常量表示 __TIME__ 编译时的时间,用"hh:mm:ss"形式的字符串常量表示 __STDC__ 当且只当编译器遵循ISO标准时,它的值是十进制常量1 __STDC__VERSION__ 如果编译器遵循C99,则这个宏的值是199901L,其

笔记3:预处理器-(2)宏定义

#define指令称为宏定义指令,通常用#define指令来定义一个宏用来代表其他东西的一个名字(如常量表达式等).通常来说预处理器会通过将宏的名字和它的定义存储在一起来响应#define指令.当这个宏在后面的程序中使用到时,预处理器会"扩展"宏,将宏替换为其定义值. 简单的宏 简单的宏的定义格式: #define 标识符 替换列表 如: #define DTE_LEN 80 #define TRUE 1 #define FALSE 0 #define PI 3.1415926 #de

BOOST_AUTO宏

在boost中,有个非常不错的宏BOOST_AUTO(),它的作用是自动给var定义类型,适合function()函数返回的值的类型. 1 int function() 2 { 3 return 10; 4 } 5 main() 6 { 7 BOOST_AUTO(var, function()); 8 } 上面的作用类适于: int function() { return 10; } main() { int var = function(); }

宏------进阶

宏定义的黑魔法 - 宏菜鸟起飞手册 宏定义在C系开发中可以说占有举足轻重的作用.底层框架自不必说,为了编译优化和方便,以及跨平台能力,宏被大量使用,可以说底层开发离开define将寸步难行.而在更高层级进行开发时,我们会将更多的重心放在业务逻辑上,似乎对宏的使用和依赖并不多.但是使用宏定义的好处是不言自明的,在节省工作量的同时,代码可读性大大增加.如果想成为一个能写出漂亮优雅代码的开发者,宏定义绝对是必不可少的技能(虽然宏本身可能并不漂亮优雅XD).但是因为宏定义对于很多人来说,并不像业务逻辑那

宏定义中使用do{}while(0)的好处 (转载)

宏定义中使用do{}while(0)的好处   #define MACRO_NAME(para) do{macro content}while(0) 的格式,总结了以下几个原因: 1,空的宏定义避免warning: #define foo() do{}while(0) 2,存在一个独立的block,可以用来进行变量定义,进行比较复杂的实现. 3,如果出现在判断语句过后的宏,这样可以保证作为一个整体来是实现: #define foo(x) /action1(); /action2(); 在以下情况

Clojure语言十三: 宏

micro的核心作用 由于micro接收的参数可以很复杂,而且不求值,因此可以接收list,在内部转换,加工后执执行,也可以接收完全不是lisp的语法,在内部转换成clojure能执行的list. 这样可以创建自己的DSL,而把clojure宏实现为DSL解析器. micro与function的区别 特点是允许在Clojure evaluate你的list之前,你能够像处理函数一样的处理它, 但是不evaluate. 如果你想把一个表达式作为参数传递给函数,并要求这个参数不求值,这是做不到的.比

互联网领袖高峰对话实录:马云李彦宏等激烈碰撞

本文来自: http://tech.sina.com.cn/i/2014-11-20/detail-icesifvw7880253.shtml 视频:马云李彦宏雷军等激辩未来(精华版)(来源:新浪科技) 精华版 http://video.sina.com.cn/p/tech/other/v/2014-11-22/035564280275.html 全程 http://video.sina.com.cn/p/tech/other/v/2014-11-22/134964281959.html 中外互

iOS 中 #error宏 的使用的一个例子

头文件中如下定义宏: /** * @brief 默认空间名(必填项) */ #error 必填项 #define DEFAULT_BUCKET @"" /** * @brief 默认表单API功能密钥 (必填项) */ #error 必填项 #define DEFAULT_PASSCODE @"" 类的实现中使用: self.bucket = DEFAULT_BUCKET; self.passcode = DEFAULT_PASSCODE; 这样,如果没有初始化这两