c#如何从函数表中调用函数

本文关键字:函数 调用 | 更新日期: 2023-09-27 18:27:28

我的项目中有.NET DLL导入库,我想调用的函数的名称取自函数table (List<string>)

假设它们都有相同的返回类型和参数。

我有类似"Func1"、"Func2"的functions_table[]。。。。

我从那个表中随机选择(实际上它就像List),然后在我的程序中调用

正如我所理解的,C#委托不适用于此解决方案。

我想随机选择一个名为Func1()的函数(例如),用它们的参数从托管C#代码中调用。

如何才能做到这一点?

c#如何从函数表中调用函数

因为您说过必须从托管代码中调用此函数,所以我相信函数DLL是本机的。因此,首先,您需要一些本地方法来加载''释放此库并调用函数:

public static class NativeMethods
{
    [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
    public static extern IntPtr LoadLibrary(string filename);
    [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
    public static extern bool FreeLibrary(IntPtr hModule);
    [DllImport("kernel32.dll", CharSet = CharSet.Ansi, SetLastError = true)]
    public static extern IntPtr GetProcAddress(IntPtr hModule, string procName);
}

然后使用此代码加载DLL:

var libHandle = NativeMethods.LoadLibrary(fileName);
if (libHandle == IntPtr.Zero)
{
    var errorCode = Marshal.GetLastWin32Error();
    // put error handling here if you need
}

免费:

if (libHandle != IntPtr.Zero)
    NativeMethods.FreeLibrary(libHandle);

您还需要代理人进行通话。例如,

delegate int FuncDelegate(int arg1, bool arg2);

然后从DLL调用函数:

var func1Address = NativeMethods.GetProcAddress(libHandle, "Func1");
var func1 = (FuncDelegate)Marshal.GetDelegateForFunctionPointer(func1Address, typeof(FuncDelegate));
var result = func1(42, true);

当然,您可以(也可能应该)缓存以下函数:

private Dictionary<string, FuncDelegate> _functionsCache = new Dictionary<string,FuncDelegate>();
private int CallFunc(string funcName, int arg1, bool arg2)
{
    if (!_functionsCache.ContainsKey(funcName))
    {
        var funcAddress = NativeMethods.GetProcAddress(libHandle, funcName);
        var func = (FuncDelegate)Marshal.GetDelegateForFunctionPointer(funcAddress, typeof(FuncDelegate));
        _functionsCache.Add(funcName, func);
    }
    return _functionsCache[funcName](arg1, arg2);
}
MethodInfo handler = GetType.GetMethod("NameMethod");
handler.Invoke(context, new object[] {parameters}