奇怪的宏

作者: 罗蓁蓁 | 来源:发表于2020-05-01 12:07 被阅读0次

这一篇介绍这些奇怪的宏。

一、do while(0)

为了交换两个整型变量的值,前面值传递中已经用包含指针参数的 swap 函数做到了,这次用来实现(swap.c):

#include <stdio.h>
#define SWAP(a,b)       \
    do{                 \
        int t = a;      \
        a = b;          \
        b = t;          \
    }while(0)

int main()
{
    int c=1, d=2;
    int t;  // 测试 SWAP 与环境的兼容性
    
    SWAP(c,d);
    
    printf("c:%d d:%d\n", c, d);
    return 0;
}

这个宏看起来就有点怪了:do while(0) 是写了个循环又不让它循环,蛋疼啊!其实不然,这样写是有妙用的:

首先,SWAP 有多条语句,如果这样写:

#define SWAP(a,b)       \
        int t = a;      \
        a = b;          \
        b = t;

那么用的时候就得这么用:

SWAP(c,d)

不能加分号!加了很难看!不习惯吧?

其次,使用 do{...}while(0),中间的语句用大括号括起来了,所以是另一个命名空间,其中的新变量 t 不会发生命名冲突

SWAP 宏要比之前那个函数的效率要高,因为没有发生函数调用,没有参数传递,宏会在编译前被替换,所以只是嵌入了一小段代码。

二、##

标题我没打错,这里要说的就是井号,#的功能是将其后面的宏参数进行字符串化操作。比如下面代码中的宏:

#define WARN_IF(EXP) \
do{ if (EXP) \
    fprintf(stderr, "Warning: " #EXP "\n"); } \
while(0) 

那么实际使用中会出现下面所示的替换过程:

WARN_IF (divider == 0); 

被替换为 :

do { if (divider == 0) 
    fprintf(stderr, "Warning: " "divider == 0" "\n"); 
} while(0); 

需要注意的是:C语言中多个双引号字符串放在一起会自动连接起来,所以如果 divider 为 0 的话,就会打印出:

Warning: divider == 0

三、####

# 还是比较少用的,## 却比较流行,在 linux0.01 中就用到过。##被称为连接符,
用来将两个 记号(编译原理中的词汇) 连接为一个 记号。

看下面的例子吧(add.c):

#include <stdio.h>

#define add(Type)               \
Type add##Type(Type a, Type b){ \
    return a+b;                 \
}

// 下面两条是奇迹发生的地方
add(int)
add(double)

int main()
{
    int a = addint(1, 2);
    double d = adddouble(1.5, 1.5);
    
    printf("a:%d d:%lf\n", a, d);
    return 0;
}

那两行被替换后是这个样子的:

int addint(int a, int b){ return a+b; }
double adddouble(double a, double b){ return a+b; }

出差必备

买火车票、高铁票、机票,订酒店都打9折的出行工具TRIP,点击注册

相关文章

  • 奇怪的宏

    这一篇介绍这些奇怪的宏。 一、do while(0) 为了交换两个整型变量的值,前面值传递中已经用包含指针参数的 ...

  • 你是年少的欢喜

    一、相识 小井第一次和宏说话是一个很奇怪的场景。 宏穿着一件橘色的长棉衣,湿透了半截滴滴答答滴着水,他坐在河堤上,...

  • 奇怪的我奇怪

    感觉这段时间,或者说一直都是,说,一两个人不待见你可能是他们的问题,但如果一群人都无感可能就是你的问题了,是吗...

  • 宏宏的日常

    周未去了一趟郑州,看爸,妈文宏又冻感冒了,鼻窦炎又犯了,心疼孩子。 周未教小表弟学英语,教的挺好 晚上刚写完作业,...

  • 奇怪的人,奇怪的文字,奇怪的世界

    人真是一个奇怪的物种 ,每天都会有很多很多乱七八糟的念头:好的,坏的;善的,恶的。幸好,我是一个胆小怕事的人,从来...

  • 奇怪奇怪真奇怪

    在这个幻想大于现实的世界里,盛放着大碗大碗的鸡汤,多喝无益,但在身体疲劳时,偶尔喝上一杯,也能起个强身健体的功能。...

  • 奇怪奇怪

    突然发现昨天的自己好可怕,做了很多啥事。也许是因为遇到了不期而遇的人,再加上最近烦心的事情很多,一下子很多事情就涌...

  • 奇怪奇怪

    1到底做错了什么 无论我走到哪里 总听到有人说我风凉话 即使是在空空的小巷内 2这是我第一次下厨哦 算是庆祝我们在...

  • jni-01、宏、jni函数详解、数据获取、类型转换、签名规则

    宏语法 宏定义 解决循环拷贝的问题 T2.h 宏的取消 #undef 宏 宏变量 真实开发中:宏都是大写 宏函数...

  • 【C/C++】宏(macro)定义与使用

    文章结构如下: 宏的定义 宏的替换与代码展开 宏的替换产生的问题 获取宏参数名称 宏参数的结合 宏的取消 宏定义的...

网友评论

    本文标题:奇怪的宏

    本文链接:https://www.haomeiwen.com/subject/pyofghtx.html