C/C++中的类型转换

Posted TangguTae

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C/C++中的类型转换相关的知识,希望对你有一定的参考价值。

目录

一、C语言中的类型转换

1、隐式类型转换

2、强制类型转换

C语言类型转换的特点:

二、C++中的类型转换

1、static_cast

2、reinterpret_cast

3、const_cast

4、dynamic_cast

四种类型转换的特点:


一、C语言中的类型转换

1、隐式类型转换

适用与两个相关的类型之间的自动转换,类型不相关时编译器会识别出来并报错。

double a = 3.14;
int b = a;//隐式类型转换

int* p = nullptr;
b = p;//两个不相关的类型无法进行隐式类型转换

 

2、强制类型转换

如果想让两个不相关之间的类型发生转换,此时需要显示的取强制类型转换。

int d = 3;
int *pd = nullptr;
d = (int)pd;//强制类型转换

C语言类型转换的特点:

1、转换的格式很简单。

2、转换的可视性较差。

3、没有错误检查,容易出错。

二、C++中的类型转换

为了解决C语言类型的转换的问题,C++引入了四种命名的强制类型转换操作符。

1、static_cast

static_cast用于非多态类型的转换,负责相关连的两个类型之间进行类型转换,与C语言中的隐式类型转换类似。

double val1 = 3.3;
int val2 = static_cast<int>(val1);//用于两个相关类型的转换

2、reinterpret_cast

强制转换,用于两个不相关的类型的转换,简单来说什么类型都可以转,这种转换不对结果做保证,容易出问题。

typedef void(*fuc)(void);
void* test(int num)

	cout << "test: " << num << endl;
	return nullptr;

int main()

    fuc val3 = reinterpret_cast<fuc>(test);//把一个void*返回值、int类型的参数的函数转换成ret = void和参数为void的函数
    val3();

运行结果难以预料。

 

3、const_cast

去除变量的常属性只针对指针和引用。

 

const int a = 3; //常变量
int* pa = &a; //这样将a的地址赋值给pa是错的,因为a的地址是const int*类型

//此时可以采用const_cast 来进行强转
const int a = 3;
int* pa = const_cast<int*>(&a);//此时可以把const int* 转换成int*

补充:如果此时对pa指向的空间修改同时打印a 的值和 *pa的值会发生什么

*pa = 4; // pa指向的空间更改
cout << a << endl; //输出3  编译器的优化,默认从寄存器读取,此时采用volatile关键字修饰
cout << *pa << endl; //输出4

可以看到a的值确实改变,但为什么会输出3呢?

原因编译器的优化

编译器会默认的认为常变量是不会被修改的,所以会将他的值拷贝到寄存器当中,每次获取a的值都是从寄存器中去获取,而不是从内存中读取。常变量a他在内存中的栈区间内,这个a的值是已经被修改了。

如果要避免这种情况的发生,需要用关键字volatile,他的作用是防止编译器去优化,每次读取数据从内存中读取数据

 

4、dynamic_cast

用于类的向上向下转换。

向上转换:子类向基类转换。

​向下转换:基类向子类转换。

前提:dynamic_cast只能用于含有虚函数的类。

dynamic_cast会先检查是否能转换成功,能成功则转换,不能则返回0。

class Base

public:
	virtual void functon(void)
	int a;
;
class Child :public Base

public:
	int b;
;
void test(Base* ptr)

	Child* pc1 = (Child*)ptr;//C语言中的强转

	Child* pc2 = dynamic_cast<Child*>(ptr);//C++中的转换,会判断是否能够转换成功
	
	cout << "pc1: " << pc1 << endl;
	cout << "pc2: " << pc2 << endl;


//main函数
Base b;
Child c;

test(&b);//给一个基类的地址
test(&c);//给一个子类的地址

向下转换是一个很不安全的过程,转换的时候会进行类型检查,类型相等成功转换,类型不等转换失败。但是C语言中的强转不管结果怎样,很危险。

 如果传入一个基类的地址进去的时候,强转之后 如果此时访问一下子类的成员,会出现错误。

四种类型转换的特点:

1、转换明确,调用什么样的类型转换一眼便知道

2、可以进行错误检查。

以上是关于C/C++中的类型转换的主要内容,如果未能解决你的问题,请参考以下文章

C/C++中的类型转换

C/C++中的类型转换

C/C++ 中的类型转换到底是啥?

c/c++类型转换相关总结

C#中的委托是啥?事件是否一种委托?

手动将字符串转换为 int 并检查 C/C++ 中是不是发生溢出?