PInvoke互操作技术
代码编写
--- Person.cpp
extern "C"
{
_declspec(dllexport) int Sum(int a, int b);
}
--- Person.h
#include "Person.h"
#include "iostream"
using namespace std;
int Sum(int a, int b)
{
return a + b;
}
class Program
{
[DllImport("ConsoleApplication1.dll", CallingConvention = CallingConvention.Cdecl)]
extern static int Sum(int a, int b);
static void Main(string[] args)
{
var result = Sum(10, 20);
Console.WriteLine($"10+20={result}");
Console.ReadLine();
}
}
---- output -----
10+20=30
--- main.cs
class Program
{
delegate void Callback(int a);
[DllImport("ConsoleApplication1.dll", CallingConvention = CallingConvention.Cdecl)]
extern static void AsyncProcess(Callback callback);
static void Main(string[] args)
{
AsyncProcess((i) =>
{
//这里回调函数哦...
Console.WriteLine($"这是回调函数哦: {i}");
});
Console.ReadLine();
}
}
------- output -------
这是回调函数哦: 10
--- Person.cpp
extern "C"
{
//函数指针
typedef void(_stdcall* PCALLBACK) (int result);
_declspec(dllexport) void AsyncProcess(PCALLBACK ptr);
}
--- Person.h
#include "Person.h"
#include "iostream"
using namespace std;
void AsyncProcess(PCALLBACK ptr)
{
ptr(10); //回调C#的委托
}
环境配置
- 用vs2019创建C++的Console App,修改两个配置: 将程序导出为dll,修改成compile方式为Compile as C++ Code (/TP)


c#访问控制
- c#中的成员函数、变量必须保持与类前定义权限一致,与c++相比,必须在类前加访问控制
一般情况(4种)
- public:public关键字表示类成员对外部代码是完全可见和可访问的。即其他类或代码可以直接访问标记为public的成员。这是最开放的访问级别
- private:private关键字表示类成员只能在当前类内部访问,其他类无法访问标记为private的成员。这实现了数据隐藏和封装,确保类的实现细节对外部代码是不可见的
- protected:protected关键字表示类成员只能在当前类内部和其子类中访问。这允许继承体系中的子类访问基类的受保护成员,但对于其他类仍然是不可见的
- internal:internal关键字表示类成员只能在当前程序集内部访问。这个访问级别对于模块化代码和库的内部实现很有用,它允许不同的程序集使用相同的internal成员,但对于其他程序集是不可见的
特殊情况(2种)
- protected internal:protected internal关键字表示类成员可以在当前程序集内部和其子类中访问。它是protected和internal的结合,对于继承体系中的子类和同一程序集的其他类都是可见的。
- private protected:private protected关键字表示类成员可以在同一程序集内部和其派生类中访问,但是对于其他程序集的类是不可见的。它是private和protected的结合