c语言学习资料第9章 预处理命令.doc

合集下载
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

第9章预处理命令
宏定义不是c语句,所以不能在行尾加分号。

如果加了分号则会连分号一起进行置换。

可以用#undef命令终止宏定义的作用域。

对程序中用""括起来的内容(即字符串内的字符),即使与宏名相同,也不进行置换。

宏定义只做字符替换,不分配内存空间。

宏名不是变量,不分配存储空间,也不能对其进行赋值。

在宏展开时,预处理程序仅对宏名作简单的字符串替换,不作任何检查。

在进行宏定义时,可以引用已定义的宏名
无参宏定义的一般格式:
#define 标识符字符串
将这个标识符(名字)称为“宏名”,在用预编译时将宏名替换成字符串的过程称为"宏展开"。

#define是宏定义命令。

带参宏定义的一般格式:
#define 宏名(形参表)字符串
带参宏的调用和宏展开:
调用格式:宏名(实参表);
宏展开(又称为宏替换)的方法:用宏调用提供的实参直接置换宏定义中相应的形参,非形参字符保持不变。

定义有参宏时,宏名与左圆括号之间不能留有空格。

否则,C编译系统会将空格以后的所有字符均作为替代字符串,而将该宏视为无参宏。

有参宏的展开只是将实参作为字符串,简单地置换形参字符串而不做任何语法检查。

为了避免出错,可以在所有形参外,甚至整个字符串外,均加上一对圆括号。

如:#define S(r) 3.14*(r)*(r)
则:areapS(a^b); 展开后为:area^ 3.14*(a^ b)*(cH- b);
调用有参函数时,是先求出实参的值,然后再复制一份给形参。

而展开有参宏时,只是将实参简单地置换形参。

函数调用是在程序运行时处理的,为形参分配临时的内存单元;而宏展开则是在编译前进行的,在展开时不分配内存单元,不进行值的传递,也没有’返回值"的概念。

调用函数只可得到一个返回值,而用宏可以设法得到几个结果。

在有参函数中,形参都是有类型的,所以要求实参的类型与其一致;而在有参宏中,形参和宏名都没有类型,只是一个简单的符号代表,因此,宏定义时,字符串可以是任何类型的数据。

使用宏次数多时,宏展开后源程序变长,因为每展开一次都是程序增长,而函数调用不会使源程序变长。

宏替换不占用运行时间,只占编译时间。

而函数调用则占用运行时间(分配单元、保留现场、值传递、返回\ 在程序中如果有带实参的宏,则按#define命令行中指定的字符串从左到右进行置换。

如果字符串中包含宏中的形参,则将程序语句中相应的实参(可以是常量、变量或表达式)代替形参。

如果宏定义中的字符串中的字符不是参数字符,则保留。

通常如果调用库函数,则用<>,使用用户自己编写的文件,则用""。

两种格式的区别仅在
于:
⑴使用"”:系统首先到当前目录下查找被包含文件,如果没找到,再到系统指定的"包含文
件目录”去查找。

⑵使用<> :直接到系统指定的"包含文件目录”(include)去查找。

预编译时不作任何检查。

只有编译已被宏展开后的源程序时才会发现语法错误并报错。

通常情况下,源程序中所有的行都参加编译,但有时希望对其中一部分内容只在满足一定条件才进行编译,则需要用到条件编译。

(1)一般格式
#ifdef 标识符
程序段1 ;
#else
程序段2;
#endif
它的作用是若指定的标识符已经被#define命令定义过,则在程序编译阶段编译程序段1 , 否则,
编译程序段2。

其中,#else部分可以没有。

2)#ifndef标识符
程序段1
#else
程序段2
#endif
它的作用是若指定的标识符未被#define命令定义过,则在程序编译阶段编译程序段1 ,否则,编译程序段2.o
(3)#if表达式
程序段1
#dse
程序段2
#endif
它的作用是当指定的表达式的值为真(非零),则在程序编译阶段编译程序段 1 ,否则,编译程序段2.
(1) 一个#include命令只能指定一个被包含文件,如果要包含n个文件,要用n个#indude 命令。

(2) 如果文件1包含文件2 ,而在文件2中要用到文件3的内容,则可在文件1中用两个include
命令分别包含文件2和文件3,而且文件3应出现在文件2之前即在filel.c中定义。

(3) 在一个被包含文件中又可以包含另一个被包含文件,即文件包含是可以嵌套的。

(4) 在#include命令中,文件名可以用双撇号或尖括号括起来。

⑸被包含文件(file2.h)与其所在的文件(即用#indude命令的源文件file2.c),在预编译后已成为同一个文件(而不是两个文件X因此,如果file2.h中有全局静态变量,它也在filel.h 文件中有效,不必用extern声明。

如果需要修改程序中常用的一些参数,可以不必修改每个程序,只需将这些参数放在一个头文
件中,在需要是修改头文件即可,但,被包含文件修改后,凡包含此文件的所有文件都要全部重新编译。

相关文档
最新文档