我正在尝试创建一个函数,该函数需要auto_ptr
Base
类,我想用auto_ptr
来调用它Derived
类。但是我未能完成它。
我尝试在没有参考的情况下使用它:
void function(std::auto_ptr<Base> ptr);
std::auto_ptr<Derived> derivedPtr( new ... )
function(derivedPtr); // error: #348: more than one user-defined conversion from
// "std::auto_ptr<Derived>" to "std::auto_ptr<Base>" applies
并附有参考:
void function(std::auto_ptr<Base>& ptr);
std::auto_ptr<Derived> derivedPtr( new ... )
function(derivedPtr); //error: #304: no instance of overloaded function "function"
// matches the argument list
编辑: 我知道auto_ptr已被弃用,但我只能访问C++03
而无法访问boost
。因此,如果答案集中在问题本身上,我将不胜感激:)我也确实理解函数接受引用和按值auto_ptr的区别。在我的实际代码中,该函数拥有auto_ptr
的所有权,因此如果我可以从Derived
转换为Base
工作,那么两者都很好。
您正在尝试按值和引用auto_ptr
,这是完全不同的事情。按值调用意味着您将所有权转移到函数中,因为auto_ptr
副本上执行此操作。通过引用调用意味着只有保留所有权的函数外部的auto_ptr
。
由于这种差异非常不直观,因此auto_ptr
在 2011 年的标准中已被弃用,作者一直在阻止使用auto_ptr
更长的时间。总之:
根本不要使用auto_ptr
。
如果要将所有权转移到函数中,请使用unique_ptr
;如果要将其保留在函数外部,请使用引用或纯指针。这取决于您的实际情况。
更新:由于您提到必须在没有 boost 的情况下使用 C++03,因此 C++03 有一个unique_ptr实现:http://howardhinnant.github.io/unique_ptr03.html 它使用了一些可以轻松手写的增强功能,因此应该可以将其移植到您的平台而无需使用增强。
您可以毫不含糊地进行投射:
function(static_cast<std::auto_ptr<Base> >(derivedPtr));
请注意,要使其正常工作,Base
必须具有虚拟析构函数。否则,代码具有未定义的行为。
模棱两可的原因是 Arne 在他的回答中所说 - 调用方并不明显function
采用值还是引用,因此调用方并不明显,他们的auto_ptr
是否会通过调用被释放,如果释放,它是否转换为可以正确delete
指针的类型。模棱两可的转换 AFAIK 可以阻止您编写如此困难的代码。通过强制转换,可以在调用代码中显式发布derivedPtr
。
手动管理内存比使用内存auto_ptr
更好,因为它的使用充满了错误。
最好使用工业实力替代品:在最坏的情况下,检查自由主义boost
,并确定是否可以编写自己的克隆。
法利姆,写下你自己的改编owning_ptr
. 同时创建一个ownomg_ptr_transfer
类template
。 在owning_ptr
上块复制构造,位启用从owning_ptr_transfer
隐式转换,这需要底层的poimter。 具有将基础指针移动到传输对象的自由函数或方法。
本质上,如果必须,请使用 C++03 编写自己的unique_ptr
。
如果你不会使用别人的解决方案,也不会编写自己的解决方案,那么只需手动记忆即可。auto_ptr
不值得:与unique_ptr
相比,它不仅是次优的,它实际上是有害的:其目的是使内存管理更容易,相反,它使它更容易出错。 这是一个实验,它失败了。