如何通过"新"运算符阻止类分配?(我想确保我的RAII类总是在堆栈上分配.)

Kev*_*vin 44 c++ operator-overloading c++-faq

我想确保我的RAII类总是在堆栈上分配.

如何通过"新"运算符阻止类分配?

Kev*_*vin 54

您需要做的就是声明类'new operator private:

class X
{
    private: 
      // Prevent heap allocation
      void * operator new   (size_t);
      void * operator new[] (size_t);
      void   operator delete   (void *);
      void   operator delete[] (void*);

    // ...
    // The rest of the implementation for X
    // ...
};  
Run Code Online (Sandbox Code Playgroud)

有效地使'operator new'私有化可以防止类外的代码使用'new'来创建X的实例.

要完成任务,您应该隐藏'operator delete'和两个运算符的数组版本.

从C++ 11开始,您还可以显式删除这些函数:

class X
{
// public, protected, private ... does not matter
    static void *operator new     (size_t) = delete;
    static void *operator new[]   (size_t) = delete;
    static void  operator delete  (void*)  = delete;
    static void  operator delete[](void*)  = delete;
};
Run Code Online (Sandbox Code Playgroud)

相关问题: 是否可以防止对象的堆栈分配,并且只允许用"new"来填充它?

  • 理查德,不,这些方法永远不会被调用,因为它们只是被声明但没有被定义.不同之处在于私有访问会产生链接器错误而不是编译器错误. (6认同)
  • 这不会阻止 `X *x = ::new X;`,它显式调用全局运算符 new,而不是类运算符 new... (4认同)
  • 另一点是,这只会阻止从类层次结构外部调用"new".即."X"的成员可以调用该函数.新的C++'0x feature"= delete"将允许您显式停止调用该函数. (3认同)

DrP*_*zza 6

我不相信你的动力.

有充分的理由在免费商店创建RAII课程.

例如,我有一个RAII锁定类.我有一条通过代码的路径,只有在某些条件成立时才需要锁定(它是一个视频播放器,我只需要在渲染循环期间保持锁定,如果我有一个视频加载和播放;如果没有加载,我不需要它).因此,在free store上创建锁(使用scoped_ptr/auto_ptr)的能力非常有用; 它允许我使用相同的代码路径,无论我是否必须取出锁.

即是这样的:

auto_ptr<lock> l;
if(needs_lock)
{
    l.reset(new lock(mtx));
}
render();
Run Code Online (Sandbox Code Playgroud)

如果我只能在堆栈上创建锁,我就不能这样做....