首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

C++:43---派生类向基类转换、静态动态的类变量

二、转换的本质 派生类可以转换为基类的本质是: ①为什么派生类可以转换为基类:派生类从基类而来,因此派生类中包含了基类的方法和成员。...此时基类可以通过指针或引用指向派生类(相当于将派生类从基类中继承的那部分方法和成员绑定到基类上了,相当于派生类被截断了),然后基类就可以将派生类假装是一个基类对象来使用(调用其中的成员/方法) ②为什么基类不能转换为派生类...如果将一个基类对象绑定到派生类的指针/引用上,此时派生类通过指针/引用访问自己新定义的成员/方法时,发现找不到(因此不能将基类转换为派生类) 例如:下面B继承于A,子类继承于父类,同时为父类的成员开辟了空间...三、继承方式对类型转换的影响 遵循下面3个规则: 假设B继承于A ①只有当B公有地继承A时,用户代码才能使用派生类向基类转换;如果B是受保护的/私有的继承于A,则不能使用派生类向基类转换 因为保护或者私有继承...,因为其只能与自己类型一致的对象绑定到一起 演示案例 当我们使用基类的引用(或指针)时,我们并不清楚该引用(或指针)所绑定的对象的真实类型,该对象可能是基类的对象,也可能是派生类的对象。

1.8K10

《Effective C++》读书笔记(2):构造析构赋值运算

class SomeClass: private Uncopyable{ ... }; ---- 条款7、为多态基类声明virtual析构函数 C++中多态性质体现于虚函数:基类指针或引用调用虚函数时会检查指向的对象是基类还是派生类...当这样的一个指向派生类的基类指针析构时,如果析构函数不是虚函数,则直接调用基类的析构函数,那么派生类获取的资源未释放,则会造成内存泄漏。...而当析构函数是虚函数时则先调用对应的派生类析构函数,再调用基类析构函数,资源全部释放。...对于派生类的构造函数而言,进入其中时基类部分已构造完而派生类部分未构造完,对象类型是基类,故而此时调用虚函数,实际上使用的是基类的虚函数。 析构函数同理。...进入析构函数后派生类部分呈未定义值,对象类型是基类,调用的是基类的虚函数。 总而言之,在构造函数与析构函数中虚函数的行为有特殊变化;为了避免出错,不要在其过程中使用虚函数。

16330
  • 您找到你想要的搜索结果了吗?
    是的
    没有找到

    C++ 继承:代码传承的魔法棒,开启奇幻编程之旅

    通过观察表格不难发现,三种继承方法在访问限制上的约束:public 通过public继承基类的成员到派生类中,它们访问的方式是不会发生变化的;通过protected...二.基类和派生类的转换 派生类的对象可以赋值给基类的指针或者引用(赋值兼容转换),可以通过切分来形容这个过程,编译器将派生类中属于基类的空间切分出来,使指针,或者引用指向基类空间的起始位置。...指针的指向,指向的是基类那一部分 引用,引用的是基类的那一部分 class person { public: person() : _name() , _age(18) , _tel...基类对象不能赋值给派生类对象 基类对象可以通过强制类型转焕赋值给派生类的指针或者引用,但基类的指针必须指向派生类对象时才是安全的,具体细节后续在介绍。...赋值运算符重载的行为 派生类的operator=必须要调用基类的operator=完成基类的赋值。

    11010

    【C++】三大特性之继承

    ---- 二、基类和派生类对象赋值转换 派生类对象 可以赋值给 基类的对象 / 基类的指针 / 基类的引用。这里有个形象的说法叫切片或者切割。寓意把派生类中父类那部分切来赋值过去。...基类对象不能赋值给派生类对象。 基类的指针或者引用可以通过强制类型转换赋值给派生类的指针或者引用。但是必须是基类的指针是指向派生类对象时才是安全的。...派生类的operator=必须要调用基类的operator=完成基类的复制。 派生类的析构函数会在被调用完成后自动调用基类的析构函数清理基类成员。...继承允许你根据基类的实现来定义派生类的实现。这种通过生成派生类的复用通常被称为白箱复用(white-box reuse)。术语“白箱”是相对可视性而言:在继承方式中,基类的内部细节对子类可见 。...继承一定程度破坏了基类的封装,基类的改变,对派生类有很大的影响。派生类和基类间的依赖关系很强,耦合度高。 对象组合是类继承之外的另一种复用选择。新的更复杂的功能可以通过组装或组合对象来获得。

    37420

    C++:53---菱形继承、虚继承

    缺点的解决: 数据冗余:通过下面“虚继承”技术来解决(见下) 访问不明确(二义性):通过作用域访问符::来明确调用。...:为了保证公共继承对象在创建时只保存一分实例 虚继承解决了菱形继承的两个问题: 数据冗余:顶级基类在整个体系中只保存了一份实例 访问不明确(二义性):可以不通过作用域访问符::来调用(原理就是因为顶级基类在整个体系中只保存了一份实例...) 共享的基类对象成为“虚基类” 说明:虚继承不会影响派生类本身,只是对虚基类进行的说明 通过在继承列表中使用virtual关键字来说明,virtual与继承说明符(public、protected、private...)的位置可以互换 演示案例 下面的ZooAnimal是一个虚基类,Bear和Raccoon分别虚继承于ZooAnimal ?...{}; 三、虚继承中的类型转换 虚继承中也可以将派生类抓换为基类,用基类的指针/引用指向于派生类 菱形继承中的类型转换 菱形继承中会发生错误,不能将派生类转换为基类 原理是差不多的,就是因为派生类中拥有多份基类的实体

    82640

    《Effective C++》读书笔记(二):构造析构赋值运算(条款05~条款12)

    析构的时候,先是派生类先析构,然后是基类析构。 书中的补充①:需要注意的是编译器产生的析构函数并非虚函数。...书中补充②编译器拒绝为类生出operator=的情况: 第一种情况:类的成员变量中,存在引用的声明 第二种情况:存在const修饰的成员变量。...p = s;//error,报错显示operator是已删除的函数 return 0; } 赋值不成功的理由很简单,引用的指向是不可以被改变的,赋值的话就说明要改变引用指向的对象。...这种现象根本的原因在于:在派生类对象调用基类的构造函数期间,由于是基类先构造,那么在此期间,此时的对象被视为是基类的对象,并且派生类的成分并没有初始化,因此C++的做法是视它们不存在,这样才能保证安全。...,通过调用了createdogs函数,创建了基类Dog的匿名对象,也就是调用了基类的构造函数,然后进入了count_Dog函数,最后再次去调用派生类的构造函数的主体!

    37110

    继承机制深度解析:从基础到进阶的完整指南

    基类和派生类间的转换 在继承体系中,基类和派生类之间可以相互转换。尤其是在多态环境中,这种转换变得尤为重要。 在 C++ 中,基类和派生类之间的转换(类型转换)主要体现在指针和引用的转换。...这种转换是安全的,不会导致数据丢失,因为派生类包含了基类的所有成员。 向下转型(Downcasting):将基类指针或引用转换为派生类。...这种转换需要谨慎,通常使用动态类型识别(如C++中的dynamic_cast)来确保类型安全。 2.1 向上转换(Upcasting) 向上转换是指将派生类的指针或引用转换为基类的指针或引用。...2.2 向下转换(Downcasting) 向下转换是指将基类的指针或引用转换为派生类的指针或引用。...(在派生类成员函数中,可以使用基类::基类成员显示访问) 需要注意的是如果是成员函数的隐藏,只需要函数名相同就构成隐藏。 注意在实际中在继承体系⾥⾯最好不要定义同名的成员。

    16710

    C++中的继承

    s; //赋值给指针 Person* ptrp = &s; 注:基类的指针或者引用可以通过强制类型转换赋值给派生类的指针或者引用。...但是必须是基类的指针是指向派生类对象时才是安全的。这里基类如果是多态类型,可以使用RTTI(RunTime Type Information)的dynamic_cast 来进行识别后进行安全转换。...并且注意到基类_num的用法是通过基类::基类成员 显示访问的。..._num) {} ⭐3.派生类的operator=必须要调用基类的operator=完成基类的复制 同样的,基类成员会去调用基类的赋值函数,如果是派生类自己的那就需要调用自己的赋值函数。...因为派生类与基类都有operator=(),因此在调用基类的operator=()的时候,需要指定类域,传入派生类的对象进行切片处理即可!

    1K30

    C++ Primer Plus习题及答案-第十三章

    但只有通过显示类型转换,才可以将基类对象的地址赋给派生类指针(向下转换),而使用这样的指针不一定安全。 9. 可以将派生类对象赋给基类对象吗?可以将基类对象赋给派生类对象吗?...仅当派生类定义了转换运算符(即包含将基类引用作为唯一参数的构造函数)或使用基类为参数的赋值运算符时,相反的赋值才是可能的。 10. 假设定义了一个函数,它将基类对象的引用作为参数。...为什么该函数也可以将派生类对象作为参数? 应为c++允许基类引用指向从该基类派生而来的任何类型。 11. 假设定义了一个函数,它将基类对象作为参数(即函数按值传递基类对象)。...按值传递对象将调用复制构造函数,由于形参是基类对象,因此将调用基类的复制构造函数,复制构造函数已基类引用为参数,该引用可以将指向作为参数传递的派生对象,最终的结构是,将生成一个新的基类对象,其成员对应于派生类对象的基类部分...按值传递对象的主要有点在于可以保护原始数据,但可以通过将引用作为const类型传递,来达到同样的目的。 13. 假设Corporation是基类,PublicCorporation是派生类。

    76990

    【C++】继承

    这里有个形象的说法叫切片或者切割。寓意把派生类中基类那部分切出来,基类指针或引用指向的是派生类中切出来的基类那部分。 • 基类对象不能赋值给派生类对象。...(对于派生类增加的成员,基类对象中也没有值可以赋) • 基类的指针或者引用可以通过强制类型转换赋值给派生类的指针或者引用。但是必须是基类的指针是指向派生类对象时才是安全的。...,其实也是因为之前提到派生类可以赋值给基类,所以基类指针或者引用也可能指向一个派生类,这种指向派生类的基类的指针或者引用就可以赋值给派生类,指向基类的指针或者引用不可以赋值。...派生类的operator=必须要调用基类的operator=完成基类的复制。...需要注意的是派生类的 operator=隐藏了基类的operator=,所以显示调用基类的operator=,需要指定基类作用域 4.

    6100

    (图解+链接易懂版)继承--C++

    这里有个形象的说法叫切⽚或者切割。寓意把派生类中基类那部分切出来,基类指针或引用指向的是派生类中切出来的基类那部分。 基类对象不能赋值给派生类对象。...基类的指针或者引⽤可以通过强制类型转换赋值给派生类的指针或者引⽤。但是必须是基类的指针是指向派生类对象时才是安全的。...需要注意的是派生类的operator=隐藏了基类的operator=,所以显示调⽤基类的operator=,需要指定基类作用域 派生类的析构函数会在被调⽤完成后⾃动调⽤基类的析构函数清理基类成员。...这种通过生成派生类的复用通常被称为白箱复用(white-box reuse)。术语“白箱”是相对可视性而言:在继承方式中,基类的内部细节对派生类可见 。...继承⼀定程度破坏了基类的封装,基类的改变,对派生类有很⼤的影响。派生类和基类间的依赖关系很强,耦合度高。 • 对象组合是类继承之外的另⼀种复用选择。新的更复杂的功能可以通过组装或组合对象来获得。

    10010

    【C++】C++中的继承,看这一篇就够了

    基类和派生类对象赋值转换 派生类对象 可以赋值给 基类的对象 / 基类的指针 / 基类的引用。这里有个形象的说法叫切片或者切割。寓意把派生类中父类那部分切来赋值过去。 基类对象不能赋值给派生类对象。...基类的指针或者引用可以通过强制类型转换赋值给派生类的指针或者引用。但是必须是基类的指针是指向派生类对象时才是安全的 三. 继承中的作用域 在继承体系中基类和派生类都有独立的作用域。...派生类的拷贝构造函数必须调用基类的拷贝构造完成基类的拷贝初始化。 派生类的operator=必须要调用基类的operator=完成基类的复制。...(2)菱形继承是指一个类同时从两个直接或间接的基类继承,而这些基类又共同继承自同一个基类,形成了一个菱形结构。这种情况下,可能会导致数据冗余和访问不明确(二义性)的问题。...当在基类中使用虚拟继承时,派生类中只会存储一份基类的数据成员,通过虚基表(Vtable)和虚基表指针来管理这些共享数据,从而避免了数据冗余。

    11710

    领悟面向对象就离开发应用不远了(类提高)有你对面向对象的所有疑问,爆肝1w字

    而必须通过基类的方法进行访问,具体的说就是派生类的构造函数必须使用基类的构造函数,其他的类比 RatedPlayer :: RatedPlayer(unsigned int r,const &fn,const...注意:如果在派生类中重新定义基类的方法,通常将基类方法声明为虚的,好处是程序将根据对象类型而不是引用或者指针的类型来选择方法版本,算是一个惯例吧 函数实现我就不写了,不然篇幅太长了,感谢!...虚函数 虚函数源于c++中的类继承,是多态的一种。在c++中,一个基类的指针或者引用可以指向或者引用派生类的对象。同时,派生类可以重写基类中的成员函数。...基类中 可以在基类中将被重写的成员函数设置为虚函数,其含义是:当通过基类的指针或者引用调用该成员函数时,将根据指针指向的对象类型确定调用的函数,而非指针的类型。...值得注意的是 只能通过指向基类的指针或基类对象的引用来调用虚函数,其格式为:指向基类的指针变量名->虚函数名(实参表)或基类对象的引用名.虚函数名(实参表) 实现动态联编需要同时满足以下三个条件:

    53220

    每日一问06 构造函数可以是虚函数吗

    是有构造函数特点决定的 虚函数使用条件必须是通过指针或者引用调用 构造函数无法通过指针直接调用。只能通过 placement new方式调用。...我的误区 根本说不清楚:直接回答vptr构造 不相关, 不懂 构造函数无法通过指针访问原理,new 如何调用类构造函数申请的用法。...根本说不清楚:必须创建好了,才能用,不懂 抽象和具体关系.接口不属于具体一个类 析构函数可以是虚函数吗,为什么 参考思路: 可以是 析构函数 执行顺序是 派生类 ,基类 如果析构函数不被声明成虚函数,则编译器实施静态绑定...,在删除指向派生类的基类指针时,只会调用基类的析构函数而不调用派生类析构函数,这样就会造成派生类对象析构不完全。...如果声明了,触发 派生类 ,基类 正确析构顺序。

    70930

    C++:继承与派生

    面使用,实际中扩展维护性不强 二、基类和派生类对象赋值转换 1、派生类对象 可以赋值给 基类的对象 / 基类的指针 / 基类的引用。...; Person* pp = &sobj; Person& rp = sobj; //反之 基类对象不能赋值给派生类对象 sobj = pobj; } 3、基类的指针或者引用可以通过强制类型转换赋值给派生类的指针或者引用...但是必须是基类的指针是指向派生类对象时才是安全的。这里基类如果是多态类型,可以使用RTTI(RunTime Type Information)的dynamic_cast 来进行识别后进行安全转换。...派生类的拷贝构造函数必须调用基类的拷贝构造完成基类的拷贝初始化。 3. 派生类的operator=必须要调用基类的operator=完成基类的复制。...②:当前对象与包含的对象是一个低耦合关系,如果修改包含对象的类中代码不需要修改当前对象类的代码。 ③:对象组合是通过获得对其他对象的引用而在运行时刻动态定义的。

    18610

    【C++】从零开始认识继承

    父类 = 子类,会对子类进行切片,把父类的部分给基类进行赋值。 也可以使用引用和指针,同样也是通过切片来进行赋值。都可以对派生类进行修改。 引用 引用就是创建一个子类中基类部分的别名。...指针 指针就是将子类中基类的地址赋值给基类指针。 注意: 派生类对象 可以赋值给 基类的对象 / 基类的指针 / 基类的引用。这里有个形象的说法叫切片或者切割。...寓意把派生类中父类那部分切来赋值过去。 基类对象不能赋值给派生类对象。 基类的指针或者引用可以通过强制类型转换赋值给派生类的指针或者引用。但是必须是基类的指针是指向派生类对象时才是安全的。...派生类的拷贝构造函数必须调用基类的拷贝构造完成基类的拷贝初始化。 派生类的operator=必须要调用基类的operator=完成基类的复制。..._d = 5; return 0; } 来看调试的过程: 通过这个逐语句调试的内存变化,我们可以确定大致的内存情况: 不使用虚拟继承就是这样的内存情况,也好理解为什么同名变量的两份是如何储存的了

    8110

    解锁C++继承的奥秘:从基础到精妙实践(上)

    2.1 向上转换(Upcasting) 向上转换是指把派生类对象的指针或引用赋值给基类的指针或引用。由于派生类继承了基类的所有公开和受保护成员,基类可以“容纳”派生类对象的一部分。...这意味着通过基类指针或引用访问派生类对象时,无法直接访问派生类中特有的成员函数或属性。 如果基类中的方法使用了虚函数(virtual),则在运行时会调用派生类中的重写方法(即多态)。...2.2 向下转换(Downcasting) 向下转换是指将基类的指针或引用转换为派生类的指针或引用。因为派生类通常比基类包含更多的信息,向下转换是有风险的,必须小心使用。...在这种情况下,调用派生类对象时,即使是通过基类的指针或引用,也会调用派生类中覆盖的函数。...析构函数:基类的析构函数如果是虚函数,派生类对象被销毁时会先调用派生类的析构函数,再调用基类的析构函数。这在使用指向基类的指针删除派生类对象时尤为重要。

    17310

    C++之继承

    面使用,实际中扩展维护性 二、基类和派生类对象赋值转换 1.派生类对象 可以赋值给 基类的对象 / 基类的指针 / 基类的引用。...这里有个形象的说法叫切片或者切割。寓意把派生类中父类那部分切来赋值过去。 2.基类对象不能赋值给派生类对象。 3.基类的指针或者引用可以通过强制类型转换赋值给派生类的指针或者引用。...但是必须是基类的指针是指向派生类对象时才是安全的。...派生类的拷贝构造函数必须调用基类的拷贝构造完成基类的拷贝初始化。 3. 派生类的operator=必须要调用基类的operator=完成基类的复制。 4....这里是通过了B和C的两个指针,指向的一张表。这两个指针叫虚基表指针,这两个表叫虚基表。虚基表中存的偏移量。通过偏移量可以找到下面的A。

    10410

    【C++修炼之路】15.C++继承

    因为可以切割,却不能补充,因此这样在引用/指针的时候是不对的。 当然,也不绝对,有几个例子是可以将基类对象赋值给派生类对象的,但这里知道即可,后续会补充上。 3....基类的指针或者引用可以通过强制类型转换赋值给派生类的指针或者引用。但是必须是基类的指针是指向派生类对象时才是安全的。...派生类的operator=必须要调用基类的operator=完成基类的复制。 派生类的析构函数会在被调用完成后自动调用基类的析构函数清理基类成员。...即B中地址指向的大小为20,C中地址指向的大小为12,通过左侧内存已的两段地址相减,正好一一对应,而这两个数字就是举例虚基类对象的偏移量。为什么会有偏移量?...继承一定程度破坏了基类的封装,基类的改变,对派生类有很大的影响。派生类和基类间的依赖关系很强,耦合度高。 对象组合是类继承之外的另一种复用选择。新的更复杂的功能可以通过组装或组合对象来获得。

    55700

    学过 C++ 的你,不得不知的这 10 条细节!

    那么可能在读取未初始化的值会导致不明确的行为。 为了避免不确定的问题,最佳的处理方法就是:永远在使用对象之前将它初始化。...最后还有一个情况:如果某个基类将 operator= 函数声明为 private ,编译器将拒绝为其派生类生成 operator= 函数。...多态性质基类需声明 virtual 析构函数 如果在多态性质的基类,没有声明一个 virtual 析构函数,那么在 delete 基类指针对象的时候,只会调用基类的析构函数,而不会调用派生类的析构函数,...问题出在 pa 指针指向派生类对象,而那个对象却经由一个基类指针被删除,而目前的基类没有 virtual 析构函数。...说明,基类构造期间 virtual 函数绝不会下降到派生类阶层。取而代之的是,对象的作为就像隶属于基类类型一样。

    75520
    领券