You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C#如何将存储在变量中的Type类型用作DllImport方法的参数类型

问题原因

C# 是静态类型语言,方法参数类型必须为**编译期可确定的类型。你代码中定义的myType是存储运行时类型信息的变量,不能直接作为参数类型使用,同时[DllImport]特性要求P/Invoke方法的签名、封送规则必须在编译阶段完成校验,不支持传入运行时Type变量作为参数类型。

可行实现方案

方案1:编译期类型别名(最推荐)

如果你的需求是统一管理P/Invoke方法的参数类型,可在文件顶部使用using指令定义编译期类型别名,编译时会自动替换为对应的实际类型,完全兼容[DllImport]语法要求。
完整示例代码:

using System.Runtime.InteropServices;
using System;
// 顶部定义类型别名,全局统一管理参数类型
using HWndType = System.IntPtr;

public class Prog
{
    public static void Main() {
        var handle = new IntPtr(12345);
        SetForegroundWindow(handle);
    }
    
    [DllImport("user32.dll")]
    public static extern bool SetForegroundWindow(HWndType hWnd);
}

方案2:运行时动态调用原生函数

如果确实需要在运行时动态指定参数类型,不能使用静态[DllImport]声明,需要手动加载动态库、获取函数地址、构造委托进行调用,示例代码如下:

using System.Runtime.InteropServices;
using System;

public class Prog
{
    public static Type myType = typeof(IntPtr);
    // 定义与原生函数匹配的委托签名
    [UnmanagedFunctionPointer(CallingConvention.Winapi)]
    public delegate bool SetForegroundWindowDelegate(IntPtr hWnd);

    public static void Main() {
        IntPtr user32Lib = LoadLibrary("user32.dll");
        IntPtr funcAddress = GetProcAddress(user32Lib, "SetForegroundWindow");
        var SetForegroundWindow = Marshal.GetDelegateForFunctionPointer<SetForegroundWindowDelegate>(funcAddress);
        
        var handle = new IntPtr(12345);
        SetForegroundWindow(handle);
    }

    [DllImport("kernel32.dll", SetLastError = true)]
    private static extern IntPtr LoadLibrary(string lpFileName);

    [DllImport("kernel32.dll", SetLastError = true)]
    private static extern IntPtr GetProcAddress(IntPtr hModule, string lpProcName);
}

内容的提问来源于stack exchange,提问作者Danny

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.30 15:15:02