繁体   English   中英

从Derived **转换为Base * const *

[英]Conversion from Derived** to Base*const*

请在链接parashift之前阅读我的问题,我可以谷歌搜索,这是略有不同的情况。

这是不允许的

Child **cc;
Base ** bb = cc;

因为你可以做到

*bb = new OtherChild;

但如果我们有

Child **cc;
const Base *const *const bb = cc;

我不认为所有这些const都是我的例子所必需的,但只是为了确定..

我认为最小的应该是

Base *const *bb = cc;

那你不能这样做

*bb = new OtherChild;

所以它应该是安全的。 但为什么不允许呢?

你有两个案例令人困惑:

  • const的加法
  • Upcasts

虽然正式(在计算机科学理论中)这两个都涉及子类化,但事实是这些的C ++规则是不同的,因为const TT表示保证是相同的,而Base*Derived*的表示Derived*通常因偏移而不同(但涉及虚拟继承时可能完全不同)。

在3.9.3中,标准声明了这一点

类型的cv限定cv非限定版本是不同类型; 但是,它们应具有相同的表示和对齐要求

鉴于:

struct Base {};
struct Derived : Base {};
Derived* pd = nullptr;
Base* pb = pd;

const确实可以通过你建议的方式添加。

Base const* const* const cpcpcb = &pb;
Base* const* pcpb = &pb; // legal, pointer can't be changed
Base const* * ppcb = &pb; // illegal, one could try to rebind the pointer
                          // to a truly const object, then
                          // use pb to mutate the const object

Derived*Base*之间没有任何关系。 存在转换,但Derived*变量不一定包含Base对象的地址( Derived对象中的Base子对象可能具有不同的地址)。 因此,您抱怨的行和您的问题所假设的行都是非法的

Base const* const* const cpcpcd = &pd; // error, there's no address of a Base
                                       // to be found in pd
Base* const* pcpd = &pd; // error: again, there's no address of a Base
                         // stored in pd

形式上,标准在4.10中描述了这一点:

类型为“指向cv D指针”的prvalue,其中D是类类型,可以转换为类型为“指向cv B指针”的prvalue,其中BD的基类。如果B是不可访问或模糊的基数D类,需要这种转换的程序是不正确的。转换的结果是指向派生类对象的基类子对象的指针。空指针值被转换为目标类型的空指针值。

转换的结果是prvalue,它没有地址,并且您无法创建指向它的指针。

这是C ++语言强加的约束,因为指针类型的隐式转换基于继承规则(隐式转换为void *除外)。

也就是说,给定以下程序,只有在TU的基础时才允许赋值:

T const *x;
U *y;
x = y;

但是,在你的情况下:

typedef Base *T;
typedef Child *U;

BaseChild之间的关系不会转移到它们的指针类型。 因此,“指向Base指针”和“指向Child指针”之间没有继承关系,以允许您想要的直接赋值。

我认为在你的等式中你期望const比它真正发挥更大的作用。

const是一个限定符,简单地说,它的作用是规范你访问类型或变量的方式。

重点是,如果语言本身,甚至没有考虑const是什么,已经规定了给定的行为,那么您的具体案例与该FAQ报告的案例没有什么不同。

你处在一个非常简单的环境中,你应该用更简单的术语来思考。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM