#include<iostream>
class A {
public:
virtual bool isB() = 0;
};
class B : public A{
public:
B() { }
bool isB() {std::cout << " not B\n"; return true;}
};
class C : public A {
public:
C() { }
bool isB() {std::cout << " not B\n"; return false;}
};
int main() {
B b;
A& a = (b.isB()) ? a(B()) : a(C()); // here is the problem
}
我也试过把它静态的转换成子类的指针,但是好像效果不太好。在真实的代码中,myfunction接受一个引用作为参数,条件依赖于代码的其他部分。
1条答案
按热度按时间uurv41yg1#
如果我没有理解错您的问题,您希望创建
B
或C
示例,具体取决于a.isB()
,其中a
是对A
的给定引用。a
可以引用B
或C
示例。基于
a
创建B
或C
的示例非常简单:上面的代码不是很有用。你想要一个有效的
A&
引用你刚刚创建的示例。在C++中你不能同时创建一个A&
和示例化一个派生对象。Reference必须总是引用已经存在的东西。所以你的代码不能工作。另外,对A的任何引用(其引用存在于if语句之后的b
或c
)将是悬空引用:一旦退出任一分支的作用域,示例就会被析构。因此,你必须使用指针,最好是智能指针。你可以写一个函数
它根据输入变量
createB
从B
或C
示例返回std::unique_ptr<A>
。在您的代码中,可以这样调用它:
请记住,变量
x
必须比xref
存在,否则xref
是一个悬空引用,使用它是未定义的行为。注意这个函数接受一个bool,而不是
A const&
。我个人更喜欢这种风格,因为签名std::unique_ptr<A> create(A const& a)
不能正确地表达意图。我会被这种方式搞糊涂。如果你有两个以上的派生类,你可以让create
接受一个枚举,其中每个值对应一个派生类。下面是完整的代码:https://godbolt.org/z/EEqPMvhdE