c和c++作为早期的开发语言,积累了大量的可用库。后续的开发语言,虽然在易用性和容易程度上面有了很大的提高,但是对于曾经的开发库,是无法做到弃之不用的。因此,对于c#语言来说,也是一样的。今天就来讨论下如何用c#调用dll这个问题。
1、首先编写一个c++代码
注意这里的c++代码是生成动态库,不是生成exe文件。后续c#就是使用这个动态库里面的函数。假设函数的内容是这样的,
extern "C" __declspec(dllexport) int add(int x, int y)
{
return x + y;
}
extern "C" __declspec(dllexport) int sub(int x, int y)
{
return x - y;
}
2、生成动态库之后,准备c#代码
namespace ConsoleApp1
{
class Program
{
static void Main(string[] args)
{
}
}
}
初始创建工程后,一般什么内容也没有。这时候,需要做的第一步,就是添加InteropServices,即,
using System.Runtime.InteropServices;
接着,第二步就是,从dll中引用导出来的函数。从上面c++的内容看,导出的函数有两个,一个是add,一个是sub,
[DllImport("Dll1.dll", EntryPoint = "add", CallingConvention = CallingConvention.Cdecl)]
public static extern int add(int a, int b);
[DllImport("Dll1.dll", EntryPoint = "sub", CallingConvention = CallingConvention.Cdecl)]
public static extern int sub(int a, int b);
注意,这两个声明最好放在class里面。有了这两个声明之后,就可以开始准备使用这两个函数了,这也是所谓的第三步动作,
static void Main(string[] args)
{
Console.WriteLine(add(1,2));
Console.WriteLine(sub(1,2));
}
有了上面的三步操作,不出意外的话,其实是可以看到3和-1这样的打印了,如下图所示,
3、总结
前面说到了c#调用了c++。总结一下主要有这么两点,第一,调用的时候传参和出参最好是基本的数据,比如char、int、char*、float、double这样的数据。第二,动态库一定要是extern "C" __declspec(dllexport)这样来定义,只有这样,才能将不确定性降到最低。最后为了方便大家复现这个问题,给出完整的c#参考代码,希望对大家有所裨益。
using System;标签:调用,sub,c#,System,dll,int,add,CallingConvention From: https://blog.51cto.com/feixiaoxing/5881300
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Runtime.InteropServices;
namespace ConsoleApp1
{
class Program
{
[DllImport("Dll1.dll", EntryPoint = "add", CallingConvention = CallingConvention.Cdecl)]
public static extern int add(int a, int b);
[DllImport("Dll1.dll", EntryPoint = "sub", CallingConvention = CallingConvention.Cdecl)]
public static extern int sub(int a, int b);
static void Main(string[] args)
{
Console.WriteLine(add(1,2));
Console.WriteLine(sub(1,2));
}
}
}