给定一个抽象接口(interface)和一个从该接口(interface)派生的实现,其中构造函数受到保护(只能从类工厂创建这些对象 - 以实现 DI 模式),我如何在工厂函数中使用 make_shared ?
例如:
class IInterface
{
public:
virtual void Method() = 0;
};
class InterfaceImpl : public IInterface
{
public:
virtual void Method() {}
protected:
InterfaceImpl() {}
};
std::shared_ptr<IInterface> Create()
{
std::shared_ptr<IInterface> object = std:: make_shared<InterfaceImpl>();
return object;
}
make_shared 显然不能访问 InterfaceImpl 中的 protected 构造函数,甚至在 IInterface 中,给我以下错误
error C2248: 'InterfaceImpl::InterfaceImpl' : cannot access protected member declared in class 'InterfaceImpl'
所以阅读这里(问题:How to make boost::make_shared a friend of my class),我尝试将以下内容放入实现类中:
friend std::shared_ptr<InterfaceImpl> std::make_shared<InterfaceImpl>();
它仍然无法编译。因此,我也将另一个放入 IInterface 类中。还是没有喜悦。我在这里做错了什么?
编辑:用于编译的完整源文件,带有“ friend ”...
#include <memory>
class IInterface
{
public:
friend std::shared_ptr<IInterface> Create();
virtual void Method() = 0;
};
class InterfaceImpl : public IInterface
{
public:
virtual void Method() {}
protected:
friend std::shared_ptr<IInterface> Create();
InterfaceImpl() {}
};
std::shared_ptr<IInterface> Create()
{
std::shared_ptr<IInterface> object = std::make_shared<InterfaceImpl>();
return object;
}
void main()
{
std::shared_ptr<IInterface> i = Create();
}
最佳答案
使用 VC10,您链接到的解决方案不起作用 - InterfaceImpl
实例的构造不会发生在 make_shared
, 但在 std::tr1::_Ref_count_obj<Ty>::_Ref_count_obj(void)
中的内部类型中.
我只想制作 Create()
功能一个friend
在你的情况下,不要使用 make_shared()
:
class InterfaceImpl : public IInterface {
// ...
protected:
friend std::shared_ptr<IInterface> Create();
InterfaceImpl() {}
};
std::shared_ptr<IInterface> Create() {
return std::shared_ptr<IInterface>(new InterfaceImpl());
}
... 或使用自定义 make_shared()
您实际上可以在不依赖丑陋的实现细节的情况下成为 friend 的实现。
另一种方法是使用类似这样的东西 pass-key-idiom :
class InterfaceImpl : public IInterface {
public:
class Key {
friend std::shared_ptr<IInterface> Create();
Key() {}
};
InterfaceImpl(const Key&) {}
};
std::shared_ptr<IInterface> Create() {
std::shared_ptr<IInterface> object =
std::make_shared<InterfaceImpl>(InterfaceImpl::Key());
return object;
}
关于c++ - 将 make_shared 与 protected 构造函数 + 抽象接口(interface)一起使用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3541632/