关于继承中的强制类型转换

dynamic_cast是与继承相关的类型转换关键字
dynamic_cast要求相关的类中必须有虚函数
用于直接或者间接继承关系的指针(引用)之间
-指针:
  转换成功:得到目标类型的指针
  转换失败:得到一个空指针

-引用:
  转换成功:得到目标类型的引用
  转换失败:得到一个异常操作信息

编译器会检查dynamic_cast的使用是否正确
类型转换的结果只可能在运行阶段才能得到

#include <iostream>
#include <string>

using namespace std;

class Base
{
public:
    Base()
    {
        cout << "Base::Base()" << endl;
    }
    ~Base()
    {
        cout << "Base::~Base()" << endl;
    }
};

class Derived : public Base
{

};

int main()
{
    Base* p = new Derived;

    Derived* pd = p;

    if( pd != NULL )
    {
        cout << "pd = " << pd << endl;
    }
    else
    {
        cout << "Cast error!" << endl;
    }

    delete p;

    return 0;
}


进一步改进:使用dynamic_cast关键字

int main()
{
    Base* p = new Derived;

    Derived* pd = dynamic_cast<Derived*>(p);

    if( pd != NULL )
    {
        cout << "pd = " << pd << endl;
    }
    else
    {
        cout << "Cast error!" << endl;
    }

    delete p;

    return 0;
}

为什么使用了dynamic_cast关键字后,编译还会出错?再看一下上边的规则,是因为类中没有虚函数。这个地方我们还需要去定义一个虚函数吗?完全没有必要,根据工程经验,但凡一个类被定义为父类,虚构函数就定义为虚函数。

class Base
{
public:
    Base()
    {
        cout << "Base::Base()" << endl;
    }

    virtual ~Base()
    {
        cout << "Base::~Base()" << endl;
    }
};

假设此时p就指向一个父类对象,即

int main()
{
    Base* p = new Base;

    Derived* pd = dynamic_cast<Derived*>(p);  //不能使用一个子类指针指向一个父类对象

    if( pd != NULL )
    {
        cout << "pd = " << pd << endl;
    }
    else
    {
        cout << "Cast error!" << endl;
    }

    delete p;

    return 0;
}

小结:

new/delete会触发构造函数或者析构函数的调用
构造函数不能成为虚函数
析构函数可以成为虚函数(可以避免内存泄露,还有一个好处使用dynamic_cast)
构造函数和析构函数中都无法产生多态行为
dynamic_cast是与继承相关的专用转换关键字

原文地址:https://www.cnblogs.com/-glb/p/11973663.html

时间: 2024-10-08 17:08:59

关于继承中的强制类型转换的相关文章

C#中的强制类型转换与as转换的区别

C#中的强制类型转换 例如有ClassA与ClassB两个类创建两个类的对象进行转换 1 2 ClassA a = new ClassA();  ClassB b = new ClassB(); 如果使用强制转换 1 ClassB c = (ClassB)a; 会报InvalidCastException异常 无法将类型为ClassA的对象强制转换为类型ClassB 若使用as关键字进行转换则 1 2 3 4 5 ClassB c=a as ClassB;  if(c!=null)  {  Me

详细理解javascript中的强制类型转换

将值从一种类型转换为另一种类型通常称为类型转换,这是显式的情况:隐式的情况称为强制类型转换,JavaScript 中的强制类型转换总是返回标量基本类型值,如字符串.数字和布尔值. 如何理解: 类型转换发生在静态类型语言的编译阶段,而强制类型转换则发生在动态类型语言的运行时? 1.如果是静态语言,比如c等,所有的类型转换应该都是在编译阶段处理的吧? 2.如果是动态语言,如js等, 编译阶段会处理类型转换吗? 一.ToString 它负责处理非字符串到字符串的强制类型转换 数字的字符串化遵循通用规则

慕课网-安卓工程师初养成-2-10 Java中的强制类型转换

来源:http://www.imooc.com/code/1241 相信小伙伴们也发现了,尽管自动类型转换是很方便的,但并不能满足所有的编程需要. 例如,当程序中需要将 double 型变量的值赋给一个 int 型变量,该如何实现呢? 显然,这种转换是不会自动进行的!因为 int 型的存储范围比 double 型的小.此时就需要通过强制类型转换来实现了. 语法:( 数据类型 ) 数值 运行结果:  可以看到,通过强制类型转换将 75.8 赋值给 int 型变量后,结果为 75,数值上并未进行四舍

赋值中的强制类型转换

赋值中的类型转换 当赋值运算符两边的运算对象类型不同时,将要发生类型转换, 转换的规则是:把赋值运算符右侧表达式的类型转换为左侧变量的类型.具体的转换如下: (1) 浮点型与整型 ● 将浮点数(单双精度)转换为整数时,将舍弃浮点数的小数部分(是直接舍弃,编译器不会自动四舍五入), 只保留整数部分.将整型值赋给浮点型变量,数值不变,只将形式改为浮点形式, 即小数点后带若干个0.注意:赋值时的类型转换实际上是强制的. (2) 单.双精度浮点型 ● 由于C语言中的浮点值总是用双精度表示的,所以floa

Java中的强制类型转换

例如,当程序中需要将 double 型变量的值赋给一个 int 型变量,该如何实现呢? 显然,这种转换是不会自动进行的!因为 int 型的存储范围比 double 型的小.此时就需要通过强制类型转换来实现了. public class HelloWorld{ public static void main(String[] args) { double heightAvg1=176.2; int heightAvg2=(int)heightAvg1; System.out.println(hei

JS中的强制类型转换

<script type="text/javascript">   /*    * 强制类型转换    * 指的是将一个数据类型强制转换为其他的数据类型    * 类型转换主要指,将其他的数据类型,转换为String,Number,Boolean    *     */      /*    * 将其他的数据类型转换为String    * 方式一:    * 调用被转换数据类型的tostring()方法    * 该方法不会影响原变量,它会将转换的结果返回    * 但是

JS在if中的强制类型转换

这个属于很基础了,但是却很有用,需要的补个坑吧: JS在很多情况下会进行强制类型转换,其中,最常见两种是: 1.使用非严格相等进行比较,对==左边的值进行类型转换: 2.在if判断时,括号内的值进行类型转换,转化为布尔值: 强制转换为false的四种情况 在if中进行强制转换为false的情况只有四种,分别是: 1.数字0 2.NaN 3.空字符串 4.null或undefined But:这里存在2中特殊情况,数组和对象(因为,在上述条件下恒为true),改如何判断呢? 其实也简单:前者arr

Qt中的强制类型转换

在C++开发中经常要进行数据类型的强制转换. 刚开始学习的时候,直接对基本数据类型强制类型转换,如float fnum = 3.14; int num = (int)fnum; 随着C++标准的发展,又提供了dynamic_cast.const_cast .static_cast.reinterpret_cast等高级安全的强制转换方法. dynamic_cast: 通常在基类和派生类之间转换时使用,run-time cast.const_cast: 主要针对const和volatile的转换.

函数声明中的强制类型转换

如何写一个程序使得微处理器在启动时自动调用0位置处的子例程呢? 首先我们要找到这样的一个位置,的办法就是用一个指针指向该位置,而该位置正好又是一个我们所需要的任意类型的函数,那么问题就能得到解决.假设我们有一个指向该位置的函数指针,其类型为空.如:(*fp)().现在最重要的问题就是如何让fp指向0位置处. 我们想到了类型的强制转换.比如将整数0,转换为指向空类型的函数的指针(void(*)())0,这个指针的含义与fp的类型完全相同,我们的目的就是用它来替换fp. 所以这段代码可以写成((vo