我想知道如何解决这个问题。我不明白这个问题在问我什么:
dynamic_cast<Y>(new X)
- 要合法吗?
- 大概会成功?
首先,要合法,Y
必须是指针类型。所以让我们把问题改写为。完成此操作后,如果是一个完整的类类型,并且如果其中一个是多态类型,或者是相同的类型,或者是.dynamic_cast<Y
cv_qualifiers*>( new X )
X
X
Y
X
X
Y
如果与 相同X
,或者是 的基类,
它将成功X
。请注意,在这些情况下,dynamic_cast
具有与 相同的行为static_cast
,并且实际上对应于隐式转换,因此通常只需编写new X
,而无需任何强制转换。(有一些特殊情况可能需要强制转换,通常是在将结果传递给void*
参数时。在这种情况下,我更喜欢
static_cast
,但在这种情况下,两者的语义完全相同。)
最后,有一种特殊情况(也会成功): if
X
是多态类型,并且Y
is 。在这种情况下,确实与具有不同的语义,尽管由于返回的 from将具有类型“指向大多数派生类型的指针”,实际效果将是相同的(同样,与隐式转换相同)。void
cv_qualifiers *
dynamic_cast
static_cast
X*
new X
问题应该是:
你对 and 的定义有什么看法
X
,Y
这样下面的代码是合法的,而且转换成功了?
那么答案就相当直截了当:X
必须是完整的类型才能使new
表达式合法。动态转换对于向上转换到非虚基是有效的,因此如果Y
是指向非虚基的指针(可能是 CV 限定的,并且包括指向X
自身的指针),则转换是有效的并且成功。
此外,在多态类型(即具有虚函数的类)上,动态转换还有其他有效用途。如果X
是多态的,那么Y
可能是void *
,或者Y
可能是指向继承层次结构中任何其他类的指针X
。但是,只有当是指向基址的指针时,转换才会成功(但是,这个基址可能是虚拟的!)。Y
(现在的推理比任意动态强制转换更简单,因为我们已经知道被继承者的动态类型。一般来说,动态强制转换可以做更复杂的事情。)
在不知道 Y 和 X 的情况下,这是完全无法回答的。例如,如果 Y 是 int,那么就是非法的。否则,如果 Y 是指向多态类的指针,它可能会成功,也可能不会,但肯定没有什么“可能”。最后,这是一个相当讨厌的内存泄漏。