在析构函数中启动一个新类

时间:2013-10-31 23:29:58

标签: c++ c++11

这个问题很简单:
我想在析构函数中启动另一个类。

A类只应在其他类被破坏时释放。

struct A
{
void foo();
};


struct B
{
  B();
  ~B();
};

B::~B()
  { 
     //Something like A a();
  };

a.foo();

有一个我看不到的简单答案吗?或者这可以通过线程来处理吗?

提前致谢
Xeno Ceph

4 个答案:

答案 0 :(得分:5)

struct A {
    void foo();
};

struct B {
    ~B() {
      A a;
    }
};

你去了,A的实例将在B的析构函数中创建。当析构函数的范围关闭时,它也将被立即销毁。关于以后访问它你没有说什么,请注意。

真正的问题是,析构函数不会带走任何东西,所以对于那些残忍的小生物来说,构建任何东西根本就没有理智。

在构造函数中创建实例时可能发生的另一个问题是异常。基本上,没有详细说明,如果某些东西抛出析构函数并且你无法立即处理它,那么你就会遇到很大的问题。在构建时投掷是信号和错误的常见做法,另一方面,析构函数根本不应该抛出。这就是为什么即使在如此简单的情况下你也必须非常小心。


虽然更严重一点,你可以在其中初始化一个全局指针,如果它只是一个(愚蠢,不少)的分配。

答案 1 :(得分:2)

这是不完全相同的代码,但非常相似。

working example

#include <iostream>
#include <string>
#include <vector>

class A
{
    public:
        void foo();
};

void A::foo()
{
    std::cout << "a.foo()" << std::endl;
}

A *a = nullptr;


class B
{
    public:
        ~B();
};

B::~B()
{ 
    a = new A();
}


int main()
{
    B *b = new B();
    delete b;
    a->foo();
}

答案 2 :(得分:2)

B::~B () {
   A a;
   // Do something with class instance a to aid in the destruction of this.
}

上面有一个潜在的问题:如果A a;抛出异常怎么办?在析构函数中抛出异常通常是个坏主意。如果您知道 A a;无法抛出异常,则上述内容没有问题。如果可以扔掉的话,你应该重新考虑你在做什么。

答案 3 :(得分:1)

这是一个非常糟糕的主意。如果A抛出会发生什么?这听起来几乎就像你在某些事情超出范围时尝试执行任意代码。如果是这种情况,这是一个更好的选择,请使用Boost.ScopeExit

#include <iostream>
#include <boost/scope_exit.hpp>

int main() {
  int a = 0;
  { // Creating a new scope
    BOOST_SCOPE_EXIT_ALL(&) {
      std::cout << "In exit handler. Setting `a` to 42\n";
      a = 42;
    };
    std::cout << "Value of `a` in scope is: " << a << "\n";
  } // Ending artificial scope

  std::cout << "Value of `a` after scope is: " << a << "\n";
}

噗:

Value of `a` in scope is: 0
In exit handler. Setting `a` to 42
Value of `a` after scope is: 42

由于你的问题缺乏特异性,为什么你想要这样做,我的建议 - 以及许多人的建议 - 是这样的:确保析构函数是异常安全的。竭尽全力维护代码的这个属性。使用lambdas,其他RAII技术或ScopeExit或其他任何内容,但是可能会在析构函数中引发的内容严重受到严重阻止(例如,分配)。