c++ - PImpl 没有使用 std::unique_ptr 的用户定义构造函数
问题描述
受到@xtofl 在How do I use unique_ptr for pimpl 中的鼓励?在这里我想提出一个问题:
为什么我不能使用std::unique_ptr
没有用户定义的构造函数来实现 PImpl 习惯用法?
考虑以下代码:
#include <memory>
class X {
public:
// X();
~X();
private:
struct Impl;
std::unique_ptr<Impl> impl_;
};
int main() {
X x;
}
g++ 失败并出现以下错误
In file included from C:/MinGW64/mingw64/lib/gcc/x86_64-w64-mingw32/8.1.0/include/c++/memory:80,
from pimpl.cpp:1:
.../x86_64-w64-mingw32/8.1.0/include/c++/bits/unique_ptr.h: In instantiation of 'void std::default_delete<_Tp>::operator()(_Tp*) const [with _Tp = X::Impl]':
.../x86_64-w64-mingw32/8.1.0/include/c++/bits/unique_ptr.h:274:17: required from 'std::unique_ptr<_Tp, _Dp>::~unique_ptr() [with _Tp = X::Impl; _Dp = std::default_delete<X::Impl>]'
pimpl.cpp:3:7: required from here
.../x86_64-w64-mingw32/8.1.0/include/c++/bits/unique_ptr.h:79:16: error: invalid application of 'sizeof' to incomplete type 'X::Impl'
static_assert(sizeof(_Tp)>0,
^~~~~~~~~~~
clang 失败并出现以下错误:
In file included from pimpl.cpp:1:
...\14.16.27023\include\memory:2082:21: error: invalid application of 'sizeof' to an incomplete type 'X::Impl'
static_assert(0 < sizeof (_Ty),
^~~~~~~~~~~~
...\14.16.27023\include\memory:2296:4: note: in instantiation of member function 'std::default_delete<X::Impl>::operator()' requested here
this->get_deleter()(get());
^
pimpl.cpp:3:7: note: in instantiation of member function 'std::unique_ptr<X::Impl, std::default_delete<X::Impl> >::~unique_ptr' requested here
class X {
^
pimpl.cpp:9:12: note: forward declaration of 'X::Impl'
struct Impl;
^
Visual Studio 失败并出现以下错误:
pimpl.cpp
...\14.16.27023\include\memory(2082): error C2027: use of undefined type 'X::Impl'
pimpl.cpp(9): note: see declaration of 'X::Impl'
...14.16.27023\include\memory(2081): note: while compiling class template member function 'void std::default_delete<_Ty>::operator ()(_Ty *) noexcept const'
with
[
_Ty=X::Impl
]
...\14.16.27023\include\memory(2296): note: see reference to function template instantiation 'void std::default_delete<_Ty>::operator ()(_Ty *) noexcept const' being compiled
with
[
_Ty=X::Impl
]
...\14.16.27023\include\memory(2132): note: see reference to class template instantiation 'std::default_delete<_Ty>' being compiled
with
[
_Ty=X::Impl
]
...\14.16.27023\include\memory(2179): note: see reference to class template instantiation 'std::_Unique_ptr_base<_Ty,_Dx>' being compiled
with
[
_Ty=X::Impl,
_Dx=std::default_delete<X::Impl>
]
pimpl.cpp(10): note: see reference to class template instantiation 'std::unique_ptr<X::Impl,std::default_delete<_Ty>>' being compiled
with
[
_Ty=X::Impl
]
...\14.16.27023\include\memory(2082): error C2338: can't delete an incomplete type
...\14.16.27023\include\memory(2084): warning C4150: deletion of pointer to incomplete type 'X::Impl'; no destructor called
pimpl.cpp(9): note: see declaration of 'X::Impl'
解决方案
推荐阅读
- django - 使用 user_id 和 otp 作为输入自定义 JWT auth-token 生成
- javascript - 使用Javascript按下空格键时在文本区域输入上执行事件
- typescript - 如果属性成员是函数类型,如何在 Typescript 中动态调用
- c# - 找不到名为“Bank”的类型或命名空间(您是否缺少 using 指令或程序集引用?)
- html - UI 不会通过从自定义绑定方法更新中更新 observable 来更新
- elasticsearch - Elasticsearch 中的评分脚本插件
- php - GD 不支持 JPEG
- mongodb - 如何使用 mongo 查询使用 asp.net 核心从集合中获取特定数据
- jupyter-notebook - Jupyter notebook 不工作(无法识别代码)
- azure - VS 2019更新后运行azure函数时调试配置文件不存在错误