我有一個非常基本的反射實現,其中包括一個Type
類,它爲它所描述的類實現了對象實例化。剝離下來的有關部分,它看起來像這樣:std :: unique_ptr是自定義刪除器的手動調用析構函數的有效位置?
Type.h:
class Plugin; // forward declaration
typedef std::unique_ptr<Plugin> PluginPtr;
namespace Reflection {
class Type {
public:
explicit Type(PluginPtr(*)());
PluginPtr CreateInstance();
private:
PluginPtr(*_createInstance_Handler)();
};
}
Type.cpp:
Type::Type(PluginPtr(*createInstance_Handler)()) :
_createInstance_Handler(createInstance_Handler) {}
PluginPtr CreateInstance() { return (*_createInstance_Handler)(); }
實際實例化邏輯被收納在Plugin
類(也在其每個後代中):
Plugin.h:
class Plugin {
public:
virtual ~Plugin();
static const Reflection::Type Type;
private:
static PluginPtr CreateInstance();
Plugin.cpp
Plugin::~Plugin() {}
const Reflection::Type Plugin::Type(CreateInstance);
PluginPtr Plugin::CreateInstance() { return PluginPtr(new Plugin); }
當我嘗試編譯,我得到這些錯誤(在Visual Studio 2013):
error C2027: use of undefined type 'Plugin'
error C2338: can't delete an incomplete type
warning C4150: deletion of pointer to incomplete type 'Plugin'; no destructor called
我周圍挖一點,顯然這是造成通過std :: unique_ptr的刪除器(在它正在操作的類的類定義內發現它自己)。我在某處讀到,如果我提供自己的刪除器,這個問題就會消失。於是我重新定義PluginPtr
這樣:
typedef std::unique_ptr<Plugin, PluginDeleter> PluginPtr
的(編譯)問題確實消失,但隨後的問題,是可以/應該這樣PluginDeleter
調用~Plugin()
手動(以確保插件(和任何派生對象PluginPtr可能指向!)正確地被破壞)?而且我應該在哪裏/如何最好地聲明/定義它,以便我不會在不完整類型中遇到同樣的問題?
(或者還有更好的方法嗎?)
PS。現在處理我的源代碼,我意識到上述代碼中存在錯誤。在Type.cpp最後一行應改爲
PluginPtr CreateInstance() { return (_createInstance_Handler)(); }
'使用未定義類型的'Plugin'':你以前試過使用完整類型嗎?即在使用unique_ptr之前聲明整個類? – Geoffroy
@Geoffroy:是的。 – d7samurai
你在你的PluginDeleter中使用'delete'嗎? – Geoffroy