【发布时间】:2017-09-15 01:20:28
【问题描述】:
我遇到了一个奇怪的错误。当我尝试在返回指向基类型的唯一指针的函数中返回指向派生类型的唯一指针时,就好像返回值被降级为基类型一样。我无法访问它的任何方法或成员,如果我尝试访问,程序会出现段错误。
如果我尝试将 e1 重新分配给返回类型并调用其“eval”方法,则下面的示例会出现段错误。奇怪的是,在返回之前调用 eval 方法可以正常工作。当我使用分配的变量作为函数的参数之一时,似乎会发生这种情况,因为创建一个新对象来存储返回类型确实有效。
不幸的是,我的算法需要这样一行:
e1 = create( *e1, *e2 );
完整代码如下:
#include <memory>
#include <iostream>
class expr
{
public:
virtual int eval() = 0;
virtual ~expr() = default;
};
class add_expr : public expr
{
expr& e1;
expr& e2;
public:
add_expr( expr& e1, expr& e2 ): e1(e1), e2(e2) {}
int eval(){ return e1.eval() + e2.eval(); }
};
class int_expr : public expr
{
int value;
public:
int_expr( int value ) : value(value) {}
int eval(){ return value; }
};
std::unique_ptr<expr> create( expr& ast1, expr& ast2 );
int main()
{
auto e1 = std::unique_ptr<expr>( new int_expr( 10 ) );
auto e2 = std::unique_ptr<expr>( new int_expr( 10 ) );
e1 = create( *e1, *e2 );
// this seg faults
std::cout << e1->eval() << '\n';
// this works properly
auto e3 = create( *e1, *e2 );
e3->eval();
return 0;
}
std::unique_ptr<expr> create( expr& ast1, expr& ast2 )
{
auto r = std::unique_ptr<expr>( new add_expr( ast1, ast2 ) );
// this works properly
std::cout << r->eval() << '\n';
return r;
}
注意:我知道这个例子很荒谬,它只是一个非常大的程序的合并形式。
【问题讨论】:
-
你期待什么?您对
create的调用存储了对在您使用之前已删除的值的引用。
标签: c++ stl segmentation-fault polymorphism unique-ptr