本文转载自:http://my.oschina.net/shelllife/blog/123202

在宏定义中#和##的作用是:前者将宏定义的变量转化为字符串;后者将其前后的两个宏定义中的两个变量无缝拼接在一起转化为字符串。

1.   #: 在宏定义中,将其后的变量,转化为字符串。

eg:  #define  str(s)      #s

输出: helloworld , 就可以通过这样的的调用, printf( str(helloworld) );

2. ## : 在宏定义中,将其前后的两个变量拼接在一起。

eg: #define v(a,b,c,d)       0xa##b##c##d

//将四个字节的十六进制的数据转化为一个十六进制的整型数据

int    a  =  v(CF,AB,B0,BC);   // 即 a = 0xCFABB0BC

3. 两者的共性: 能够阻止宏定义的递归展开。可以通过中间的转换的宏,来实现参数宏的展开。

测试例子:

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h> #define ROOT "/mnt/sd/"
#define NAME "kernel.img" #define path(dir,name) dir##name
#define print(format,args...) printf(format,##args)
#define test(name) #name enum
{
MON = 1,
TUE = 2,
SUN = 7
}; int main(int argc, char *argv[])
{
//printf("macro PATH = %s\n", PATH);
//printf("path(dir,name) = %s\n", path(ROOT,NAME));
printf("path(dir,name) = %s\n", path(RO,OT)); //printf("macro TEST = %s\n", TEST);
printf("test(name) = %s\n", test(NAME));
printf("test(MON) = %s\n", test(MON));
//printf("#MON = %s\n", #MON); print("%s%s\n", ROOT,NAME); return 0;
}

C语言宏定义中的#和##的作用【转】的更多相关文章

  1. C语言在宏定义中使用语句表达式和预处理器运算符

    语句表达式的亮点在于定义复杂功能的宏.使用语句表达式来定义宏,不仅可以实现复杂的功能,而且还能避免宏定义带来的歧义和漏洞.下面以一个简单的最小值的宏为例子一步步说明. 1.灰常简单的么,使用条件运算符 ...

  2. C语言宏定义时#(井号)和##(双井号)的用法1

    #在英语里面叫做 pound 在C语言的宏定义中,一个#表示字符串化:两个#代表concatenate 举例如下: #include <iostream> void quit_comman ...

  3. C语言宏定义时#(井号)和##(双井号)的用法

    C语言中如何使用宏C(和C++)中的宏(Macro)属于编译器预处理的范畴,属于编译期概念(而非运行期概念).下面对常遇到的宏的使用问题做了简单总结. 关于#和## 在C语言的宏中,#的功能是将其后面 ...

  4. define宏定义中的#,##,@#及\符号

    define宏定义中的#,##,@#及\符号 在#define中,标准只定义了#和##两种操作.#用来把参数转换成字符串,##则用来连接两个前后两个参数,把它们变成一个字符串. 1.# (string ...

  5. 宏定义中的##操作符和... and _ _VA_ARGS_ _

    1.Preprocessor Glue: The ## Operator 预处理连接符:##操作符 Like the # operator, the ## operator can be used i ...

  6. c语言宏定义

    一. #define是C语言中提供的宏定义命令,其主要目的是为程序员在编程时提供一定的方便,并能在一定程度上提高程序的运行效率,但学生在学习时往往不能理解该命令的本质,总是在此处产生一些困惑,在编程时 ...

  7. C语言宏定义相关

    写好C语言,漂亮的宏定义很重要,使用宏定义可以防止出错,提高可移植性,可读性,方便性 等等.下面列举一些成熟软件中常用得宏定义......1,防止一个头文件被重复包含#ifndef COMDEF_H# ...

  8. 转:C语言宏定义时#(井号)和##(双井号)的用法

    转自:http://www.cnblogs.com/welkinwalker/archive/2012/03/30/2424844.html#2678295 #在英语里面叫做 pound 在C语言的宏 ...

  9. c语言宏定义#define的理解与资料整理

    1. 利用define来定义 数值宏常量 #define 宏定义是个演技非常高超的替身演员,但也会经常耍大牌的,所以我们用它要慎之又慎.它可以出现在代码的任何地方,从本行宏定义开始,以后的代码就就都认 ...

随机推荐

  1. Java中子类是否可以继承父类的static变量和方法而呈现多态特性

    静态方法 通常,在一个类中定义一个方法为static,那就是说,无需本类的对象即可调用此方法,关于static方法,声明为static的方法有以下几条限制: 它们仅能调用其他的static 方法. 它 ...

  2. mysql union出错: "Every derived table must have its own alias"

    SELECT count(*) from (SELECT province_code as area_id, count(*) from t_cas_rural_selected GROUP BY p ...

  3. 洛谷P2444 病毒 [POI2000] AC自动机

    正解:AC自动机 解题报告: 传送门! 首先看到这种题目二话不说先把trie树和fail指针建立起来 然后就想鸭,如果我们想让模式串和文本串尽量不能匹配,就要想办法让它跳fail指针,而不是继续往下走 ...

  4. Python3学习之路~2.2 简单的购物车程序

    程序:购物车程序 需求:启动程序后,让用户输入工资,然后打印商品列表允许用户根据商品编号购买商品用户选择商品后,检测余额是否够,够就直接扣款,不够就提醒 可随时退出,退出时,打印已购买商品和余额 代码 ...

  5. Rufus 制作 USB 启动盘简单教程

    制作 Windows 10 启动盘 U盘 / USB 安装盘图文教程  http://rufus.akeo.ie/downloads/rufus-2.2p.exe 1.将U盘连接到电脑,以管理员身份运 ...

  6. SparkSQL UDF使用方法与原理详解

    UDF是SQL中很常见的功能,但在Spark-1.6及之前的版本,只能创建临时UDF,不支持创建持久化的UDF,除非修改Spark源码.从Spark-2.0开始,SparkSQL终于支持持久化的UDF ...

  7. python对象反射和函数反射

    python的对象反射功能,经常在编程时使用.相比较其它的编程语言使用非常方便.反射就是用字符串来操作对象或者类,模块中的成员. 一.对象的反射 反射功能的实现,由这4个内置函数来实现(hasattr ...

  8. DevExpress使用技巧总结

    DevExpress是非常主流的.NET控件,目前全世界和中国都用很多用户使用,不过由于是英文版,初次接触的同学可能会觉得困难,这里就总结DevExpress常见的10个使用技巧. 1.TextEdi ...

  9. 浏览器测试string是否为图片

    在浏览器中直接打如下代码.其中adcd为图片转成的string data:image/jpeg;base64,abcd

  10. 017-linux正则表达式

    一.单字符表示:1.特定字符:某个具体的字符. '1' 'a' '\.'2.范围内单个字符:单个字符[] [0-9] [259] [a-z] [abc] [A-Z] [ABC] [a-zA-Z] [, ...