C和C++的区别1,函数的区别,内联函数,符号C++调用C代码,C语言调动C++

文章目录


1,默认值参数

在函数声明或者定义的时候,如果实参没有给形参传值,则按照默认值传参
默认参数是在函数编译时期,直接生成入参指令;

函数默认参数值只能传递常量;变量在编译期无法获取其值;

默认值参数只能从右向左一次生成;

可以在上卖弄函数的定义中先声明最右边的默认参数,在其下方可以只定义中间的默认参数从而达到右边起,两位设有默认参数;

函数的默认值参数在同一作用域中只能赋值一次不能多次赋值;

因为函数的默认参数值是在编译时生成入参指令,所以参数的默认值只在本文件中生效;(编译是单文件的操作)

2,内联函数
在函数前加inline 关键字即成为内联函数;

正常函数的调用:
1,传参
2,call fun()
3,开辟栈帧
4,返回值返回
5,栈帧回退
6,参数清除

内联函数:在realse(发行版本)调用点不开辟栈帧,直接展开即直接用内联函数的指令————代码展开在编译时期展开生成汇编指令展开的;
在debug(调试版本一般不对代码进行优化)版本下,内联函数和正常函数的调用方式一样;

递归函数无法成为内联函数原因:
内联函数在编译期展开,递归函数需要变量来结束,所以递归函数不可能被处理为内联函数;
inline只是对函数的建议,建议将该函数处理为内联函数(函数过大也不会成为内联函数);

编译器常常报错的两个说明:

无法解析外部符号:说明该符号未被定义;
符号重定义:说明该符号再次被定义不能再被定义;
符号:

数据:(全局变量)
所有的数据都会生成符号;
指令当中只有函数名会生成符号;
分为全局符号(global)和局部符号(local)
全局符号:所有的文件只要引用声明都可以使用;
局部符号只在本文件中可见;
编译完成后是二进制可重定位文件
链接完成生成二进制 可执行文件;

inline在debug版本下生成的是local符号,如果处理为内联函数后在realse版本不生成符号,直接在调用点展开;

宏函数:

预编译时期调用展开 ;
无法调试;
没有类型安全校验;
有栈帧开辟;
单文件可见;
不生成符号;

static函数:

不展开;
可以调试;
有内省安全校验;
有栈帧开辟;
单文件可见;
生成local符号;

内联函数:

debug不展开,release版本在函数调用点展开;
可以调试;
有类型安全校验;
debug版本有栈帧开辟release版本没有栈帧开辟;
单文件可见;
debug版本生成local符号, release不生符号;

为什么内联函数在release版本下不用生成符号?
因为内联函数在编译时就已经展开了;

为什么内联函数在debug版本下会生成local符号?

因为debug版本就是为了release版本做服务要展开用编译器编译器;编译器只针对单文件,所以要让编译器看到所以只能在当前文件存在;如果其他问就按也存在编译器则无法展开;

普通函数:

不展开;
可以调试;
有类型安全校验;
有栈帧开辟;
多文件可见;
生成gloal符号;

3,函数重载
函数名称相同参数列表不同;

函数重载是在编译时期根据参数类型决定的究竟调用哪个函数———静多态的一种
多态———静多态————编译时期的多态————早绑定;

多态:多种形态状态;

C和C++的相互调用;

C++调用C C++产生函数符号 (形参+函数名)

exter "C"
{
 void fun_C();
}

C调用C++
如果将C++的符号改为C语言的符号————需要改变C++的源文件error
添加自己实现的C++文件,然后写C++函数然后去调用需要的C++函数;然后使自己实现的C++函数产生C语言符号;之后使用C语言调用;

c语言生成函数符号依赖于函数名称;
C++生成函数符号依赖于函数名称和参数列表;

#include<iostream>
#include<stdlib.h>
using namespace std;
/*
函数的区别
函数参数的默认值
1,函数参数的默认值是怎么传入的?什么时候传入的?
通过入栈指令传入
编译期确定
函数调用先传参(从右向左传参)
指令在什么时候生成?
编译期生成指令时必须知道将函数有默认值参数并且默认值是多少?
编译期间针对的是单文件因此出错;
2,函数参数的默认值作用域在哪里?
只在当前文件
*/

/*int fun(int a, int b = 200, int c)肯定会报错默认值参数必须从右向左依次开始 */
//int fun(int a, int b, int c=300)//函数参数的默认值
//{
//	cout << a << endl;
//	cout << b << endl;
//	cout << c << endl;
//	return 0;
//}
//int fun(int a,int b,int c);//此时报错,编译时期是单文件的(挡在另一个文件里设置默认参数时)
//int fun(int a, int b, int c = 300);
int tem;
int fun(int a,int b,int c=tem);
int fun(int a,int b=200,int c);//多次默认赋值虽然报错但是依旧可以运行
/*
函数重载(函数名相同,参数列表不同)
c语言函数编译生成函数符号  依赖函数名;
*/
bool compare(int a,int b)//c语言不允许函数名重重复-compare
{
	cout << "bool compare(int a,int b)" << endl;
	return a > b;
}
bool compare(char a,char b)//-compare_char_char
{
	cout << "bool compare(char a,char b)" << endl;
	return a > b;//所以可以在c++里面使用函数的重载
}
bool compare(short a, short b)
{
	cout << "bool compare(short a,short b) " << endl;
	return a > b;
}
bool compare(float a, float b)
{
	cout << "bool compare(float a,float b)" << endl;
	return a > b;
}
//int compare(char a, char b)//返回值不同参数列表相同不是重载会报错
//{
//	return a > b;
//}
/*
内联函数
在函数调用的地方,将函数代码按照逻辑在编译期展开(在生成指令的时候展开)

inline (只是建议编译器将fun1函数处理为内联函数)

递归不可以被处理成内联
原因:递归有终结条件(变量去判断终止条件)在编译期生成指令没有获取具体的值无法判断终止条件
一直展开形成死递归

将inline int fun1(int a,int b)放到fun.cpp里面
然后只是在main.cpp里面声明一下
在main.cpp主函数里面调用fun1函数
在别的文件里找到该函数的符号的和定义体,但是无法链接,内联函数咋编译期就要展开如果在其他文件就无法展开
在编译期间无法拿到含函数的定义;
*/
//inline int fun1(int a, int b)
//{
//	int c = a + b;
//	return c;
//}
int fun1(int a, int b);//fun1_int_int *UND*
/*
传参
将下一行指令地址入栈
将ebp寄存器入栈
esp ebp 偏移 ------ 开辟栈帧
执行函数体----1ms(如果函数内容十分简单就很快结束)
返回值
栈帧回退
恢复现场
参数清除
*/

/*
符号
local符号本地符号(对外环境是屏蔽的)
inline函数产生的local符号,static也是产生local 符号;
global符号全局符号
*/

/*
普通函数
有类型安全校验;
可以调试;
生成global符号;

静态函数
有了型安全校验;
可以调试;
local符号;

宏函数
没有参数类型的校验,直接进行字符的替换
不能i调试(u无法进入函数体内);
不生成符号;

内联函数
有类型安全校验;
可以调试(直接展开为什么能进入另一个文件)---在debug版本,内联函数和静态函数表现一致
在release和宏函数表现基本一致;
在debug版本生成local符号,release不生成符号;
加个extern 生成glocal符号
*/
#define  FUN(a,b) a+b*a//宏函数在预编译的时候加开始展开按照字符展开


//如何用c++调用c语言?
/*
void fun_c(int a, int b);
fun_c_int_int  *UND无法连接c语言里面的符号是fun_c
*/
extern"C"
{
void fun_c(int a, int b);//fun_c  *UND*可以链接;
}


//如何使用c语言调用C++加一个中间层文件
extern"C"
{
//C++的函数;转化为C
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值