【问题标题】:Reference 'this' in dynamic event handler在动态事件处理程序中引用“this”
【发布时间】:2009-07-13 17:57:57
【问题描述】:

在我的“myClass”类中,我使用 Reflection.Emit 为 myClass 类的成员之一动态编写事件处理程序。

我已经成功完成了。

现在,我想修改事件处理程序以调用 myClass 类中的实例方法之一。

但是,我无法弄清楚如何使用 Reflection.Emit 将对“this”的引用推送到 MSIL 堆栈。在事件处理程序中,Ldarg_0 不是对“this”的引用,而是事件处理程序的第一个参数。

有谁知道如何在堆栈上推送对“this”的引用,以便我可以调用实例方法。例如,这就是我希望 c# 代码的样子:

public class myClass
{
private myObj1 obj1;
public myClass() {
   this.init();
}

private void init()
{
   obj1.myEvent += new myEvent_EventHandler(theHandler);
}

private void theHandler(myObj2 obj2, myObj3 obj3)
{
   // this is the part I'm having trouble with
   this.myFunction(obj2);
}

private void myFunction(myObj2 obj2)
{
   // irrelevant
}
}

谢谢!

【问题讨论】:

  • 当您说“Main”时,您指的是实际类还是启动程序的static void main 方法?根据 Jakers 的回答,似乎有些混乱。
  • 对不起,糟糕的选择。我会修改
  • 您不能从静态方法调用实例方法,因为没有实例可以调用它。
  • 这里没有什么是静态的,我写了一个代码示例

标签: c# reflection event-handling cil reflection.emit


【解决方案1】:

当你使用Reflection.Emit(我在这里假设DynamicMethod)时,可以选择生成代码的第一个参数是什么,它可以通过隐式传递代表,像这样:

using System;
using System.Reflection.Emit;

public class App
{
    static void Main()
    {
        DynamicMethod m = new DynamicMethod("test", typeof(void),
            new[] { typeof(App), // <-- type of first argument, your choice
                typeof(string) });

        var cg = m.GetILGenerator();

        cg.Emit(OpCodes.Ldarg_0);
        cg.Emit(OpCodes.Ldarg_1);
        cg.EmitCall(OpCodes.Call,
            typeof(App).GetMethod("ShowString"), null);

        cg.Emit(OpCodes.Ret);

        Action<string> d = (Action<string>) 
            m.CreateDelegate(typeof(Action<string>), 
            new App()); // <-- this is the first argument, *your* choice

        MyEvent += d;

        // Trigger event
        MyEvent("Hello there");
    }

    static event Action<string> MyEvent;

    public void ShowString(string s)
    {
        Console.WriteLine(s);
    }
}

【讨论】:

  • 这是完美的答案!非常感谢!
【解决方案2】:

如果您在 main 中,则没有您的 Main 类的实例。主要功能是静态的。

【讨论】:

    猜你喜欢
    • 2020-09-18
    • 2013-07-13
    • 2013-06-26
    • 2016-04-17
    • 1970-01-01
    • 2015-06-26
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多