2

假设我有一个充当“智能指针”的类,并在销毁时释放某种系统资源。

class Resource{
protected:
     ResourceHandle h;
public:
     Resource(ResourceHandle handle)
     :h(handle){
     }

     ~Resource(){
         if (h)
             releaseResourceHandle(h);//external function, probably from OS
     }
};

我有一些函数返回用于初始化“资源”的值:

ResourceHandle allocateHandle();

现在,如果我在我的代码中这样做:

Resource resource(allocateHandle());

AND allocateHandle()抛出异常,究竟会发生什么?崩溃会发生在 Resource() 构造期间还是构造之前?

常识告诉我,因为在 allocateHandle 返回之前抛出异常,执行甚至不会进入 Resource() 构造函数,但我不确定。这是一个正确的假设吗?

4

5 回答 5

4

参数在任何函数调用之前进行评估——在这种情况下是构造函数——。因此,在构造函数调用之前抛出异常

于 2010-07-25T14:56:41.890 回答
3

是的,你是对的(正如其他人所说)。

但是你在暗示什么(我认为)。
如果进入构造函数并抛出异常,对象会发生什么。

析构函数是否仍会被执行?

仅当构造函数实际完成时才会触发析构函数(如果抛出异常而使构造函数转义,则构造函数未完成)。在这种情况下,没有输入构造函数,因此对象不存在,因此不会执行析构函数。

如果在构造函数执行时抛出异常会发生什么。
在这种情况下,因为构造函数没有完成,析构函数也永远不会被执行,但是所有的成员字段呢?如果构造函数通过异常离开,则所有完全形成的成员都将调用其析构函数(完全形成的成员是其构造函数已被调用并成功完成的成员)。

于 2010-07-25T17:01:35.740 回答
1

这是一个正确的假设。

于 2010-07-25T14:55:56.010 回答
1

如果编译器进入构造函数,它可以从一个没有返回的函数中传入什么值?

于 2010-07-25T14:59:25.287 回答
0

是的,你的假设是正确的。

此时,您只是创建参数并将它们推入堆栈。“资源”的对象甚至都没有形成!

因此,异常不会在堆栈展开期间调用析构函数。

于 2010-07-25T14:59:11.080 回答