reinterpret_cast

reinterpret_cast的原型为:reinterpret_cast<typeid> (expression).type_id必须是一个指针,引用,算术类型,函数指针,成员指针等。它可以把一个整型转换为指针,也可以把一个指针转换为整型。总结来说,reinterpret_cast可以允许任何指针类型(引用)之间的转换,整型与指针类型间的转换以及指针与足够大的整型之间的转换。

reinterpret_cast转换的实质是让编译器重新给出对象的比例模型而不进行二值转换。也就是让编译器按照目标转换类型在内存中所占的比特位重新编译原始数据类型。转换前后对象的地址值是不变的,只是对象的读取内存的比例变了而已。

虽然reinterpret_cast有很强的转换功能,但是不能乱用。IBM的C++指南、C++之父Bjarne Stroustrup的FAQ网页MSDN的Visual C++也都指出:错误的使用reinterpret_cast很容易导致程序的不安全,只有将转换后的类型值转换回到其原始类型,这样才是正确使用reinterpret_cast方式。比如下面的代码:

typedef int (*FunctionPointer)(int); 
int value = 21; 
FunctionPointer funcP; 
funcP = reinterpret_cast<FunctionPointer> (&value); 
funcP(value);

在这里我们定义一个函数指针,参数类型为int,返回值类型为int。我们讲一个int型数据的地址值赋给函数指针,然后将int型数据作为参数传递给函数。这段代码虽然可以编译通过,但是会得到"EXC_BAD_ACCESS"的运行错误,因为我们通过funcP所指的地址找到的并不是函数入口。

// ConsoleApplication29.cpp : 定义控制台应用程序的入口点。
//

#include "stdafx.h"
#include<iostream>
#include<string>
using namespace std;
class CBaseX
{
public:
	int x;
	
	CBaseX() { x = 10; 
	cout <<"CBaseX() " << endl;
	}
	void foo() { printf("CBaseX::foo() x=%d/n", x); }
};
class CBaseY
{
public:
	int y;
	int *py;
	CBaseY() { y = 16; py = &y;
	cout <<"CBaseY() " << endl;
	}
	void bar() {
		cout << y << endl;
		cout << py<< endl;
		//printf("CBaseY::bar() y=%d, *py=%d/n", y, *py);
	}
};
class CDerived : public CBaseX, public CBaseY
{
public:
	int z;
}; //情况1:两个无关的类之间的转换

int _tmain(int argc, _TCHAR* argv[])
{   int n = 9;
    double d =reinterpret_cast<double&>(n);
	cout << d << endl;
	CBaseY* pY3 = new CBaseY();
	printf("CBaseY* pY3 = %d/n", (int)pY3);
	
	CDerived* pD3 = reinterpret_cast<CDerived*>(pY3);
	printf("CDerived* pD3 = %d/n", (int)pD3);
	cout << pD3->y <<" "<<pD3->py<<" "<<pD3->z<< endl;
	system("pause");
	return 0;
}

在以上例子中,将int型的n转换为double型,由于int型数据类型在内存中占4个字节,而double型数据类型在内存中占8个字节,因此使用reinterpret_cast进行转换时,编译器在原对象地址处读取8字节内容,多读了4字节。

而在将py3转换为pd3的过程中,编译器将按照CDerived占用内存的比例模型重新读取py3中的内容。因此编译器会将Py3中的y认为是pd3中的x,py3中的py当成是pd3中的y。


  • 4
    点赞
  • 20
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值