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

C#中如何判断Action的Invoke被触发及对应调用的实例对象?

解决方案

核心原理

C# 中的多播委托内置GetInvocationList()方法,可获取所有注册到该委托的子委托条目,每个条目包含两个关键属性:

  • Method:存储注册方法的完整反射信息,可用于校验当前是否为目标方法myMethod
  • Target:存储方法所属的实例对象(如果是静态方法则该属性为null)

实现方案1:触发侧遍历调用列表校验

你可以不直接调用Event.Invoke(),改为手动遍历所有子委托逐个触发,同时做校验和实例识别,修改后的DoInvokeTest代码如下:

public void DoInvokeTest()
{
    if (Event == null) return;
    // 获取所有注册的委托条目
    var invocationList = Event.GetInvocationList();
    foreach (Delegate del in invocationList)
    {
        // 校验是否为TheClass类定义的myMethod方法,避免同名方法误判
        if (del.Method.Name == nameof(myMethod) && del.Method.DeclaringType == typeof(TheClass))
        {
            // 提取方法所属的实例
            var targetInstance = del.Target as TheClass;
            // 此处可自定义校验逻辑,比如判断是否为目标实例theclassObj
            Console.WriteLine($"待调用myMethod的实例哈希值:{targetInstance.GetHashCode()}");
            
            // 执行当前委托
            del.DynamicInvoke();
            
            // 标记方法已调用完成
            Console.WriteLine($"实例[{targetInstance.GetHashCode()}]的myMethod已执行完成");
        }
        else
        {
            // 其他注册方法直接执行
            del.DynamicInvoke();
        }
    }
}

实现方案2:方法内部直接获取所属实例

如果你不需要在触发侧做逻辑,只需要确认方法被调用时的所属实例,直接在myMethod内部通过this关键字即可获取:

public void myMethod()
{
    // this即为当前方法所属的TheClass实例
    Console.WriteLine($"myMethod已被调用,所属实例哈希值:{this.GetHashCode()}");
    // 此处也可以直接加日志或者打标记,确认方法执行
}

注意事项

  • 不要向事件注册匿名方法/Lambda表达式,这类方法的Target为编译器自动生成的闭包对象,无法直接匹配到业务实例
  • 静态事件的注册方法需要手动解绑,否则会导致实例无法被GC回收,引发内存泄漏

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.24 10:06:00