我如何在c#中使用c ++ dll

时间:2010-08-26 10:28:20

标签: c# c++ dll import unmanaged

我喜欢在我的c#应用程序中导入c ++ dll我怎么能这样做?我需要使用什么概念?

4 个答案:

答案 0 :(得分:3)

您需要查看不同类型的互操作。最简单的是P/Invoke。那就是COM Interop。然后最后你可以使用Managed C++

答案 1 :(得分:2)

可以访问C ++库源

最干净的方法是使用C++ Interop创建一个包装器作为混合模式程序集。这允许您使用托管和非托管的编译指示在本机代码和托管代码之间切换。通过这种方式,您可以使用托管C ++包装器很好地包装C ++类,并从(当然)托管C#中调用它。

请注意,这在Mono下无效。

无权访问C ++库源,但知道一点C ++?

由于C ++本身调用COM的独特能力,您可以在托管C ++中编写一个小的托管包装来调用非托管C ++库。

这是使用custom runtime callable wrappers, or CRCWs完成的。然后,您可以使用本机.Net类型和所有。

直接从C#调用托管包装器

这样做的好处(如MSDN所述):

  
    

互操作代码内置于应用程序中,因此不依赖于单独的程序集。此外,公开的托管界面可以自定义为更像.NET。例如,RenderFile方法采用System.String而不是char *。 COM接口的托管版本称为自定义运行时可调用包装器(CRCW)。

  

无法访问C ++库源并且不了解C ++?

然后你被C++ COM Interop困住了,这有点混乱。您需要使用Tlbimp.exe生成包装器。

这很乱,因为:

  1. 托管代码中没有直接匹配的类型作为IntPtr指针类型公开(在C#中很难处理)
  2. 生成的assemlblies将非常大,因为生成库中所有内容的接口(不仅仅是你想要的东西)。
  3. 您必须在应用程序中部署额外的程序集并管理版本控制等......

答案 2 :(得分:1)

假设使用MinGW编译的this DLL。 在C-sharp中你可以遵循以下代码:

using System.Runtime.InteropServices;
using System;

class call_dll {

  [StructLayout(LayoutKind.Sequential, Pack=1)]
  private struct STRUCT_DLL {
    public Int32  count_int;
    public IntPtr ints;
  }

  [DllImport("mingw_dll.dll")]
  private static extern int func_dll(
      int an_int,
      [MarshalAs(UnmanagedType.LPArray)] byte[] string_filled_in_dll,
      ref STRUCT_DLL s
   );

  public static void Main() {

    byte[] string_filled_in_dll = new byte[21];


    STRUCT_DLL struct_dll = new STRUCT_DLL();
    struct_dll.count_int = 5;
    int[]  ia = new int[5];
    ia[0] = 2; ia[1] = 3; ia[2] = 5; ia[3] = 8; ia[4] = 13;

    GCHandle gch    = GCHandle.Alloc(ia);
    struct_dll.ints = Marshal.UnsafeAddrOfPinnedArrayElement(ia, 0);

    int ret=func_dll(5,string_filled_in_dll, ref struct_dll);

    Console.WriteLine("Return Value: " + ret);
    Console.WriteLine("String filled in DLL: " + System.Text.Encoding.ASCII.GetString(string_filled_in_dll));

  }
}

答案 3 :(得分:0)

This是您需要使用的概念:)