包装C+时执行析构函数+;与C#PInvoke一起使用的对象 我有一个C++类,我想在C语言中使用。为此,我试图编写一个其他C++ DLL来封装这个类(它是另一个库的一部分),具有可调用的功能(使用“ExtEngC++Sql Squtc(DLLISTUM)))。 我的想法是保留一个指向我的对象的指针,并将其发送到包装器dll中的函数,然后从那里调用该对象的方法。这看起来不错,但当对象具有解构器时会出现问题 这是我的C++包装代码:(设备是我的C++类/对象)< /P>

包装C+时执行析构函数+;与C#PInvoke一起使用的对象 我有一个C++类,我想在C语言中使用。为此,我试图编写一个其他C++ DLL来封装这个类(它是另一个库的一部分),具有可调用的功能(使用“ExtEngC++Sql Squtc(DLLISTUM)))。 我的想法是保留一个指向我的对象的指针,并将其发送到包装器dll中的函数,然后从那里调用该对象的方法。这看起来不错,但当对象具有解构器时会出现问题 这是我的C++包装代码:(设备是我的C++类/对象)< /P>,c#,c++,memory,pinvoke,marshalling,C#,C++,Memory,Pinvoke,Marshalling,这是我的C#包装代码: [DllImport("Wrapper.dll")] static extern Status Device_open(ref IntPtr objectHandler, IntPtr uri); public static Device Open(string uri) { IntPtr handle = IntPtr.Zero; Device_open(ref handle, Marshal.String

这是我的C#包装代码:

    [DllImport("Wrapper.dll")]
    static extern Status Device_open(ref IntPtr objectHandler, IntPtr uri);
    public static Device Open(string uri)
    {
        IntPtr handle = IntPtr.Zero;
        Device_open(ref handle, Marshal.StringToHGlobalAnsi(uri));
        return new Device(handle);
    }
    [DllImport("Wrapper.dll")]
    static extern void Device_Close(IntPtr objectHandler);
    public void Close()
    {
        Device_Close(this.Handle);
    }
下面是C#应用程序中的测试代码:

    Device d = Device.Open(di.URI);
    d.Close();
一切都好。问题是,当我请求打开一个新设备时,主C++对象的解构器将被执行,所以我的关闭请求总是返回异常(因为它已经关闭或被破坏);p>
我能做些什么来防止这种情况

正在销毁
设备
,因为它在
设备_open()
功能结束时超出范围。要解决此问题,请使用
new
动态分配
设备
实例,这样您就可以控制
dl
的生存期。然后
删除dl设备关闭()功能中的code>

注意,C++函数将地址分配给函数的本地代码<>代码> */COD>,调用方将无法看到该地址。要修复这个问题,在C++方面,可以通过引用传递指针:

__declspec(dllexport) Status Device_open(Device*& di, const char* uri)
或者您可以传递一个
设备**

__declspec(dllexport) Status Device_open(Device** di, const char* uri)
然而,我不确定这将如何影响c方

为防止任何内存泄漏,如果调用
dl.open(url)
失败,请确保
Device
new
实例为
delete
d:

__declspec(dllexport) Status Device_open(Device*& di, const char* uri)
{
    Status status;
    try
    {
        Device* dl = new Device();
        status = dl->open(uri);
        if (status != OK)
        {
            delete dl;
        }
        else
        {
            di = dl;
        }
    }
    catch (std::bad_alloc const&)
    {
        status = BAD_ALLOC; // Or equivalent failure reason.
    }
    return status;
}

__declspec(dllexport) void Device_Close(Device* di)
{
     // di->close(); Uncomment if destructor does not close().
     delete di;
}

只是FC++,C++中没有解构主义者。它们被称为析构函数。:)@jalf,谢谢你的小费+我试过了,它解决了我的问题。使用设备*&我的C代码不需要任何更改。但如果它是一个INT值或Void*?!我能为他们做什么?!我不能从它们中创建新的对象,那又怎样?忘了谢谢,:)如果这个对象(比如说设备)来自其他方法呢?!
__declspec(dllexport) Status Device_open(Device*& di, const char* uri)
{
    Status status;
    try
    {
        Device* dl = new Device();
        status = dl->open(uri);
        if (status != OK)
        {
            delete dl;
        }
        else
        {
            di = dl;
        }
    }
    catch (std::bad_alloc const&)
    {
        status = BAD_ALLOC; // Or equivalent failure reason.
    }
    return status;
}

__declspec(dllexport) void Device_Close(Device* di)
{
     // di->close(); Uncomment if destructor does not close().
     delete di;
}