代表中的方法参数

res*_*sgh 2 c# parameters delegates

我有这个方法:

public override void respond(params string[] resargs)
{
    foreach (command cmd in pndgcmds)
    {
        cmd(this);
    }

    if (objs[resargs[0]].status)
        objs[resargs[0]].request(resargs);
    else
    {
        pndgcmds.Add(
            (myclass master) =>
            {
                if (master.objs[resargs[0]].status != true) return;
                master.objs[resargs[0]].request(resargs);
                //code to remove the delegate
            });
    }
}
Run Code Online (Sandbox Code Playgroud)

检查对象是否能够响应,使其响应(如果有),否则将命令存储在字典中,以便在下次调用响应时检查并调用状态.

我有两个问题.

  1. 如何编写代码来删除委托?我不知道该怎么做.

  2. 如您所见,委托的许多内部工作依赖于方法参数.代表将如何表现?

提前致谢!

Mar*_*ell 6

匿名方法很难删除,因为captire-context的实例仅在创建时才可用,因此是必需的.幸运的是,有一个诀窍:

SomeDelegateType handler = null;
handler = (myclass master) =>
            {
                if (master.objs[resargs[0]].status != true) return;
                master.objs[resargs[0]].request(resargs);
                pndgcmds.Remove(handler);
            };
pndgcmds.Add(handler);
Run Code Online (Sandbox Code Playgroud)

现在这是一个自动取消订阅处理程序,在调用时将取消订阅.请注意,要执行此操作,我们需要存储委托实例(handler),但我们会在该变量上创建一个闭包.初始=null是明确分配的要求.

您应该注意到该resargs变量也被捕获,如果索引零处的值在订阅之后但在调用之前发生更改,则可能会导致混淆.如果你想使用"now"值,那么请关闭它:

SomeDelegateType handler = null;
string val = resargs[0];
handler = (myclass master) =>
            {
                if (master.objs[val].status != true) return;
                master.objs[val].request(resargs);
                pndgcmds.Remove(handler);
            };
pndgcmds.Add(handler);
Run Code Online (Sandbox Code Playgroud)