如何防止其他人在堆上创建一个新的类实例?

时间:2012-06-14 20:57:45

标签: c++ inheritance

  

可能重复:
  How do I prevent a class from being allocated via the 'new' operator? (I'd like to ensure my RAII class is always allocated on the stack.)

假设我在库中定义了一个类

class Base {};

我将该类发布给用户。

一个用户定义了一个新类

class Derived : public Base {}

我可以在Base中做些什么来阻止用户在堆上创建Derived的实例?

例如,允许这样做

Derived dd;

这不是

Derived* dd = new Derived();

谢谢,

3 个答案:

答案 0 :(得分:9)

我认为你能做的最好的事情是声明一个private operator new(我不记得是否需要这个但是你可能想要做所有这三个:正常,数组和您的基类中的位置)。用户仍然可以通过在Derived类中创建自己的operator new来解决这个问题,但至少他们必须考虑它并积极努力颠覆你的意图。

如果您担心在堆上创建类的非意外问题(例如子类的恶意开发人员),则C ++不是此项目的语言。它功能强大,有很多地方你必须依靠你的终端程序员而不是绕过意图。

答案 1 :(得分:4)

您在基类中将operator new设为私有。

class Base {
    void* operator new(size_t);
};
class Derived : public Base {
}

//...

Base* p = new Derived; //ERROR
Derived d;             //OK

答案 2 :(得分:0)

除了在new中将Base运算符设为私有之外,您还可以向用户提醒Base Base的意图是什么。这样,使用Base的开发人员无法声明未记录的意图。

class Base
{
    void * operator new (size_t) {}
    void * operator new[] (size_t) {}
    void * operator new (size_t, void *) {}
protected:
    struct I_promise_not_to_dynamically_allocate_Base {};
    Base (I_promise_not_to_dynamically_allocate_Base) {}
    virtual ~Base () {}
    //...
};

现在,当开发人员使用Base时,他们被迫传入参数:

class Derived : public Base
{
public:
    Derived () : Base(I_promise_not_to_dynamically_allocate_Base()) {}
    //...
};

如前所述,没有什么能阻止开发人员自己超载newdelete,但他们会违背承诺!