1 C语言指针类型转换
C语言中的指针就是裸指针,裸指针存储是指向计算机内存的某一(起始)地址,通过*
取值操作符可以进行任何操作,因此不同指针类型相互转换是比较简单的事情,如下代码:
#include <stdio.h>
#include <stdlib.h>
int main()
{
char c = 'a';
printf("c = %i\n", c);
int * ip1 = (int *)&c; //指针转换
printf("ip = %p\n", ip1);
printf("i = %c\n", *ip1);
printf("i = %i\n", *ip1);
//
int a = (int)c; //强转
printf("a = %d\n", a);
exit(0);
}
转换之后,开发者只要知道类型就可以对原有数据进行各类操作,C语言最强大的void *
类型经常作为函数参数类型。
2 C++指针类型相互转换
C++中是允许裸指针,因此裸指针之间转换方法同C语言指针强转,C++11中引入了智能指针std::shared_ptr
等,boost库种也有类似智能指针boost::shared_ptr
,智能指针转换不能通过上述方法进行强转,必须通过库提供转换函数进行转换。
C++11的方法是:std::dynamic_pointer_cast
, boost中的方法是:boost::dynamic_pointer_cast
。如下代码所示:
#include <memory>
#include <boost/shared_ptr.hpp>
#include <boost/make_shared.hpp>
#include <iostream>
class Base {
public:
Base(){}
virtual ~Base() {}
};
class D : public Base {
public:
D(){}
virtual ~D() {}
};
int main()
{
// derived class to base class
D* d1 = new D();
Base* b1 = d1;
//
std::shared_ptr<D> d2 = std::make_shared<D>();
std::shared_ptr<Base> b2 = d2;
boost::shared_ptr<D> d3 = boost::make_shared<D>();
boost::shared_ptr<Base> b3 = d3;
/*
* dynamic cast maybe failed. and return null;
*
*/
D* d11 = dynamic_cast<D*>(b1); //succ
D* d12 = static_cast<D*>(b1); //succ
typedef std::shared_ptr<D> d_ptr;
// std::shared_ptr<D> d21 = dynamic_cast<d_ptr>(b2); //compile error
std::shared_ptr<D> d22 = std::dynamic_pointer_cast<D>(b2);
typedef boost::shared_ptr<D> d_b_ptr;
// boost::shared_ptr<D> d31 = dynamic_cast<d_b_ptr>(b3); //compile error
boost::shared_ptr<D> d32 = boost::dynamic_pointer_cast<D>(b3);
return 0;
}
本代码示例下载地址
2.1 C++智能指针强转应用场景
如上述代码,假如定义一个map用来保存所有的实例:
std::unordered_map<int id, std::shared_ptr<Base>> objs;
objs.insert[1] = d21;
//拿出来的对象类型是D
std::shared_ptr<Base> o = objs[1];
//此处需要强转
//std::shared_ptr<D> dd = o; //compile error
std::shared_ptr<D> dd = std::dynamic_pointer_cast<D>(o);
//然后就可以正常调用类D所有的成员函数