简体   繁体   English

与std :: unique_ptr的clang错误

[英]clang error with std::unique_ptr

I have base object called IList . 我有一个名为IList基础对象。 Then I have VectorList , that inherits IList . 然后我有VectorList ,它继承了IList

then I have function like this: 然后我有这样的功能:

std::unique_ptr<IList> factory(){
    auto vlist = std::make_unique<VectorList>();
    return vlist;
}

This compiles without problem under gcc , but clang gives following error: 这在gcc下编译没有问题,但是clang给出了以下错误:

test_file.cc:26:9: error: no viable conversion from 'unique_ptr<VectorList, default_delete<VectorList>>' to
      'unique_ptr<IList, default_delete<IList>>'
        return vlist;

How is proper way to handle this kind of errors? 如何正确处理这种错误?

It appears (your version of) Clang is still following C++11 behaviour in this regard. 看来(你的版本)Clang在这方面仍然遵循C ++ 11的行为。 In C++11, you had to use std::move in this case, because the type of vlist is different from the return type, and so the clause of "when returning an lvalue, try it as an rvalue first" did not apply. 在C ++ 11中,你必须在这种情况下使用std::move ,因为vlist的类型与返回类型不同,因此“返回左值时,首先尝试将其作为rvalue”的子句没有应用。

In C++14, this restriction of "same types required" was lifted, and so in C++14, you shouldn't need the std::move in the return statement. 在C ++ 14中,解除了“相同类型所需”的限制,因此在C ++ 14中,您不应该在return语句中使用std::move But if you need your code to compile with your current toolchain, simply add it there: 但是如果您需要使用当前工具链编译代码,只需将其添加到那里:

return std::move(vlist);

The exact C++11 wording was this: 确切的C ++ 11措辞是这样的:

12.8/32 When the criteria for elision of a copy operation are met or would be met save for the fact that the source object is a function parameter, and the object to be copied is designated by an lvalue, overload resolution to select the constructor for the copy is first performed as if the object were designated by an rvalue. 12.8 / 32当满足或将满足复制操作的省略标准时,除了源对象是函数参数这一事实,并且要复制的对象由左值指定,重载决策选择构造函数为首先执行复制,就好像对象是由右值指定的一样。 ... ...

The criteria for copy elision (which include "same type") have to be met; 必须满足复制省略(包括“相同类型”)的标准; they're just slightly extended to cover parameters as well. 它们只是稍微扩展到覆盖参数。

In C++14 (N4140), the wording is broader: 在C ++ 14(N4140)中,措辞更广泛:

12.8/32 When the criteria for elision of a copy/move operation are met, but not for an exception-declaration, and the object to be copied is designated by an lvalue, or when the expression in a return statement is a (possibly parenthesized) id-expression that names an object with automatic storage duration declared in the body or parameter-declaration-clause of the innermost enclosing function or lambda-expression, overload resolution to select the constructor for the copy is first performed as if the object were designated by an rvalue. 12.8 / 32当满足复制/移动操作的省略标准时,但不满足异常声明,并且要复制的对象由左值指定, 或者当return语句中的表达式为a时(可能是括号内的) ) id-expression命名一个对象,该对象具有在最内层封闭函数或lambda-expression的body或parameter-declaration-clause声明的自动存储持续时间首先执行重载决策以选择复制的构造函数,就好像指定了对象一样通过右值。

(Emphasis mine) (强调我的)

As you can see, copy elision criteria are no longer required for the return case. 如您所见, return案例不再需要复制省略标准。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM