On Thursday, 27 July 2017 at 20:28:47 UTC, Moritz Maxeiner wrote:
On Thursday, 27 July 2017 at 19:19:27 UTC, SrMordred wrote:
//D-CODE
struct MyStruct{
    int id;
    this(int id){
        writeln("ctor");
    }
    ~this(){
        writeln("dtor");
    }
}

MyStruct* obj;
void push(T)(auto ref T value){
    obj[0] = value;
}

void main()
{
    obj = cast(MyStruct*)malloc( MyStruct.sizeof );
    push(MyStruct(1));
}

OUTPUT:
ctor
dtor
dtor

I didnt expected to see two dtors in D (this destroy any attempt to free resources properly on the destructor).

AFAICT it's because opAssign (`obj[0] = value` is an opAssign) creates a temporary struct object (you can see it being destroyed by printing the value of `cast(void*) &this` in the destructor).

Can someone explain why is this happening and how to achieve the same behavior as c++?

Use std.conv.emplace:

---
import std.conv : emplace;

void push(T)(auto ref T value){
        emplace(obj, value);
}
---

It worked but isnt this odd?
like, if I change the push(MyStruct(1)) for obj[0] = MyStruct(1); (which is what I expected in case of compiler inlining for example) the behavior change:
OUTPUT:
ctor
dtor

I´m having the feeling that this "auto ref T" don´t have the same behavior that the "T&&" on c++.

I find this very strange because if i copy/paste/tweak code from c/c++ on D, and have some kind of malloc/free on the ctor/dtor the code will blow in my face without warning.

Reply via email to