C++程序设计基础(4)宏定义和内联

1.知识点

1.1宏定义

(1)不带参数的宏定义

1 #define ERROR_MESSAGE -100
2 #define SECONDS_PER_DAY 60*60*60

(2)带参数宏定义,这种形式称为宏函数,但其实并不是函数

#define OUTPUTINT(x) cout<<"INT:"<<x<<endl
#define OUTPUTCHAR cout<<"CHAR:"<<x<<endl

1.2内联函数

宏定义是在预处理阶段进行宏展开的,但是经常会出现一些意想不到的错误,故出现内联函数,内联函数既发挥了宏定义的优势,又弥补了其缺点。

内联函数是在定义时在函数最前面加上inline,或者将函数声明的同时进行定义(这种方式不推荐)。

下面是一个内联函数的例子:

 1 class Rectangle {
 2 public:
 3     Rectangle(int, int);
 4     int getSquare();
 5     int getGirth() { return 2 * (length, width); }        //直接在声明时定义函数,形成内联函数
 6 private:
 7     int length;
 8     int width;
 9 };
10
11 Rectangle::Rectangle(int l,int w):length(l),width(w){}
12 inline int Rectangle::getSquare() {        //在函数定义时使用inline形成内联函数
13     return length * width;
14 }

2.面试题

2.1简述内联函数和宏定义的区别

相同点:二者都能够节省频繁的函数调用过程中所产生的时间和空间消耗,提高执行的效率;二者都是哦谈过将函数调用替换成完整的函数体,二者的实现也类似。

区别:(1)二者的根本区别在于宏定义仅仅是字符串的替换,并不是函数,而内联函数是函数。

(2)二者的代码展开发生在不同阶段,宏定义是在预处理阶段展开的,而内联函数是在编译阶段展开的。

(3)内联函数作为类的成员函数时,可以访问类的所有成员,包括公有、私有、保护成员,隐式使用this指针,而宏定义无法实现这些功能。

(4)内联函数可以完全替代宏定义,故尽量少使用宏定义。

(5)另外在使用内联函数时要注意代码膨胀问题,内联函数应该尽量简短(另外现在编译器一般都有优化功能,当检测到内联函数代码很长时,不会进行内联,即使使用了内联函数)。

2.2宏定义的宏展开错误

指出下面程序中宏定义的错误并修改

 1 #define MAX(a,b) a>b?a:b
 2 #define MUL(a,b) a*b
 3 int main(int argc, char *argv[]) {
 4     int x = 4, y = 2;
 5     int max = MAX(x, y);
 6     int product = MUL(x, y);
 7     cout << "the max is " << max << endl;
 8     cout << "the product is " << product << endl;
 9     getchar();
10     return 0;
11 }

知识点:宏定义自身缺陷主要是宏展开之后,由于运算符的优先级等原因,使得宏定义展开后的语义和预想的发生偏差。

以下时两个宏展开出错的例子

1 int product=MUL(x,y+3)
2 int max=MAX(x,y)+2
3
4 //本意是
5 int product=x*(y+3)
6 int max=(x>y?x:y)+2
7 //实际宏展开变成了
8 int product=x*y+3
9 int max=x>y?x:y+2

解决办法包括以下两点:

(1)给参数自身加上括号

(2)给整个宏定义加上括号

其修改结果如下:

#define MAX(a,b) ((a)>(b)?(a):(b))
#define MUL(a,b) ((a)*(b))

2.3内联函数的常识性问题

下列关于内联函数描述错误的是

(A)内联函数可以被重载;

(B)构造函数可以被定义成内联函数;

(C)内联函数能够减少函数调用的开销;

(D)内联函数应该在函数声明时使用inline关键字

答案:D,一定要在定义时使用inline,在声明时使用不会起到任何作用。

原文地址:https://www.cnblogs.com/ys99/p/9192725.html

时间: 2024-10-05 13:32:13

C++程序设计基础(4)宏定义和内联的相关文章

宏定义与内联函数

1.宏定义的规则和使用解析(1)宏定义的解析规则就是:在预处理阶段由预处理器进行替换,这个替换是原封不动的替换.(2)宏定义替换会递归进行,直到替换出来的值本身不再是一个宏为止.(3)一个正确的宏定义式子本身分为3部分:第一部分是#dedine ,第二部分是宏名 ,剩下的所有为第三部分.(4)宏可以带参数,称为带参宏.带参宏的使用和带参函数非常像,但是使用上有一些差异.在定义带参宏时,每一个参数在宏体中引用时都必须加括号,最后整体再加括号,括号缺一不可. 宏定义示例1:MAX宏,求2个数中较大的

关于宏定义与内联函数

//定义了这个宏之后 #define CC_SYNTHESIZE_READONLY(varType, varName, funName) protected: varType varName; public: inline virtual varType get##funName(void) const { return varName; } //执行下面语句 CC_SYNTHESIZE_READONLY(CANavigationController*, m_pRootNavigationCon

转-C++之虚函数不能定义成内联函数的原因

转自:https://blog.csdn.net/flydreamforever/article/details/61429140 在C++中,inline关键字和virtual关键字分别用来定义c++中的内联函数和虚函数,他们在各自的场合都有其各自的应用,下面将简单介绍他们各自的功能,然后在说明为什么一个函数不能同时是虚函数和内联函数(inline). 一.内联函数(inline)内联函数的目的是为了减少函数调用时间.它是把内联函数的函数体在编译器预处理的时候替换到函数调用处,这样代码运行到这

宏定义与内置函数的比较

/* time:20200415 where:gfdx man:g-7.net */ #include<iostream> using namespace std; #define doub(x)x*2 int main() { for (int i = 1; i <= 4; i++) { cout << i << '\t'<< "doubled is" << '\t'<<double(i) <<

带参宏定义和inline修饰的内联函数

带参宏定义和inline修饰的内联函数都是在编译时,用函数体替换掉宏调用或函数调用.这样用的好处是减少调用函数所花费的时间. 例如: 算法导论在讲到堆排序时说的,好的堆排序实现一般是把Left(i),Right(i),Parent(i)的实现通过宏定义或内联函数来实现,这就是因为当我们对一组数据使用堆排序时,会大量的调用left,right,parent函数定义成宏或内敛函数之后既不影响我们的代码阅读性又能是代码运行速度更快!

C++内联函数详解

1.函数调用原理 "编译过程的最终产品是可执行程序--由一组机器语言指令组成.运行程序时,操作系统将这些指令载入计算机内存中,因此每条指令都有特定的内存地址.计算机随后将逐步执行这些指令.有时(如有循环和分支语句时),将跳过一些指令,向前或向后跳到特定地址.常规函数调用也使程序跳到另一个地址(函数的地址),并在函数结束时返回.下面更详细地介绍这一过程的典型实现.执行到函数调用指令时,程序将在函数调用后立即存储该指令的内存地址,并将函数参数复制到堆栈(为此保留的内存块),跳到标记函数起点的内存单元

关于内联函数的几点总结

为什么要引入内联函数(内联函数的作用) 用它替代宏定义,消除宏定义的缺点.宏定义使用预处理器实现,做一些简单的字符替换因此不能进行参数有效性的检测.另外它的返回值不能被强制转换为可转换的合适类型,且C++中引入了类及类的访问控制,在涉及到类的保护成员和私有成员就不能用宏定义来操作. 1.内联函数与宏定义的区别: 内联函数在编译时展开,可以做一些类型检测处理.宏在预编译时展开:内联函数直接嵌入到目标代码中,宏是简单的做文本替换. C++中引入了类及类的访问控制,在涉及到类的保护成员和私有成员就不能

深入探讨 内联函数和宏定义的区别

内联函数的执行过程与带参数宏定义很相似,但参数的处理不同.带参数的宏定义并不对参数进行运算,而是直接替换:内联函数首先是函数,这就意味着函数的很多性质都适用于内联函数,即内联函数先把参数表达式进行运算求值,然后把表达式的值传递给形式参数. 内联函数与带参数宏定义的另一个区别是,内联函数的参数类型和返回值类型在声明中都有明确的指定:而带参数宏定义的参数没有类型的概念,只有在宏展开以后,才由编译器检查语法,这就存在很多的安全隐患. 使用内联函数时,应注意以下问题: 1)内联函数的定义性声明应该出现在

宏与内联函数

第一部分:宏 为什么要使用宏呢? 因为函数的调用必须要将程序执行的顺序转移到函数所存放在内存中的某个地址,将函数的程序内容执行完后,再返回到转去执行该函数前的地方.这种转移操作要求在转去执行前要保存现场并记忆执行的地址,转回后要恢复现场,并按原来保存地址继续执行.因此,函数调用要有一定的时间和空间方面的开销,于是将影响其效率.而宏只是在预处理的地方把代码展开,不需要额外的空间和时间方面的开销,所以调用一个宏比调用一个函数更有效率. 但是宏也有很多的不尽人意的地方. 在C语言中: 1.宏容易出现一