[Issue 704] `class` destructor is called even if constructor throws

d-bugmail at puremagic.com d-bugmail at puremagic.com
Thu Jan 18 17:06:33 UTC 2018


https://issues.dlang.org/show_bug.cgi?id=704

Steven Schveighoffer <schveiguy at yahoo.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |schveiguy at yahoo.com

--- Comment #13 from Steven Schveighoffer <schveiguy at yahoo.com> ---
(In reply to anonymous4 from comment #12)
> Isn't it only true for C++ that destructor can't be called on an object that
> wasn't constructed? In C++ destructor can't be called because there's no
> default initialization before constructor, but in D I think destructor can
> be called because it won't run on garbage.

It's not garbage, but it's also potentially not a valid object (what the dtor
is expecting).

I'm unsure who is responsible for cleaning up the non-GC resources. Normally
the destructor does this, but if you are throwing in the constructor, then you
could do it there. However, base constructors will not be able to catch this
condition.

If I had to define it myself, I think it shouldn't be left to the GC to clean
it up. If the destructor should be called after the constructor fails via
exception, it should happen immediately (and only the destructors for which the
constructors have completed).

e.g.:

class A
{
    int x;
    this() { writeln("A.ctor"); x = 5; }
    ~this() { writeln("A.dtor"); assert(x == 5); x = 0; }
}

class B : A
{
    int y;
    this(bool bad) { writeln("B.ctor"); super(); if(bad) throw new Exception();
y = 6; }
    ~this() { writeln("B.dtor"); assert(y == 6); y = 0; }
}

void main()
{
try { new B(true); } catch() {}
writeln("done main");
}

expected output:
A.ctor
B.ctor
A.dtor
done main

--


More information about the Digitalmars-d-bugs mailing list