我有一个基类(Base
),其构造函数将引用作为参数。在我的派生类中,它是构造函数,我调用了超类构造函数,当然我需要将引用作为参数传递。但我必须从返回类型为值的方法中获取该参数...
我将举一个简短的例子:
class Base
{
public:
Base(MyType &obj) { /* do something with the obj */}
};
class Derived : public Base
{
public:
Derived(MyOtherType *otherType) :
Base(otherType->getMyTypeObj()) // <--- Here is the error because (see *)
{
// *
// getMyTypeObj() returns a value and
// the Base constructor wants a reference...
}
};
class MyOtherType
{
public:
MyType getMyTypeObj()
{
MyType obj;
obj.setData( /* blah, blah, blah... Some data */);
return obj; // Return by value to avoid the returned reference goes out of scope.
}
};
我该如何解决这个问题?
答案 0 :(得分:3)
将Base类更改为:
class Base
{
public:
Base(const MyType &obj) { /* do something with the obj */}
};
更新:如果你想修改obj,你显然不能有const
引用。在这种情况下,您可以:
1)按值传递参数。这将有副本的开销,但避免以后必须明确释放它。
2)将MyOtherType::getMyTypeObj()
更改为
MyType& MyOtherType::getMyTypeObj()
{
MyType* obj = new MyType();
obj->setData( /* blah, blah, blah... Some data */);
return *obj;
}
在这种情况下,请记住在完成后删除对象。
答案 1 :(得分:1)
真的?你的问题有答案。将参数的类型更改为Base构造函数,或者更改getMyTypeObj()的返回值的类型,以使类型兼容。
答案 2 :(得分:0)
问题是由GetMyTypeObj()返回'obj'的副本引起的,它是基于堆栈的,因此编译器在构造函数中创建一个临时变量,其范围只是Base()构造调用。
答案 3 :(得分:0)
在我看来,有两种方法可以解决这个问题。
更改Base构造函数以按值而不是按引用接受MyType对象。这将复制临时对象并解决范围问题。
或者,您可以在Derived中复制MyType对象并将引用传递给它。
class Derived : public Base { public: Derived(MyOtherType *otherType) : Base(m_myType) , m_myType(otherType->getMyTypeObj()) { // ... } private: MyType m_myType; };
选项1更简单,我通常会推荐它 选项2以防万一其他约束阻止您更改Base构造函数,