【问题标题】:Delegate System.Action does not take 1 arguments委托 System.Action 不接受 1 个参数
【发布时间】:2012-12-25 09:58:35
【问题描述】:

动作:

readonly Action _execute;

public RelayCommand(Action execute)
             : this(execute, null)
{
}

public RelayCommand(Action execute, Func<Boolean> canExecute)
{
    if (execute == null)
        throw new ArgumentNullException("execute");
    _execute = execute;
    _canExecute = canExecute;
}

其他类的代码:

public void CreateCommand()
{
    RelayCommand command = new RelayCommand((param)=> RemoveReferenceExcecute(param));}
}

private void RemoveReferenceExcecute(object param)
{
    ReferenceViewModel referenceViewModel = (ReferenceViewModel) param;
    ReferenceCollection.Remove(referenceViewModel);
}

为什么会出现以下异常,如何解决?

委托“System.Action”不接受 1 个参数

【问题讨论】:

  • 您提交的代码没有显示发生错误的行。如果您正在使用任何 IDE,请双击错误行,IDE 将直接跳到有问题的行。如果您不使用 IDE,请阅读完整的错误日志,“文件:编号”将显示在某处。如果不查看确切的位置,就很难判断出了什么问题。话虽如此,并且从错误消息来看,我猜@JOHN 已经达到了目的。下次请附上相关代码! [这里是你尝试执行“执行”委托的地方]
  • @quetzalcoatl 你确定错误不是来自RelayCommand command = new RelayCommand((param)=&gt; RemoveReferenceExcecute(param));},这是问题所在吗?同意这种观点,应该指出这一点。
  • 在第一堂课RelayCommand,你有_execute作为Action。这是一个有 0 个参数并返回 void 的委托类型。我们看不到_execute 是如何使用的。但它可能类似于_execute();(注意:0 个参数)。在“其他类”中,您的方法CreateCommand 似乎创建了一个RelayCommand,但是(除非CreateCommand 主体内还有更多内容)它看起来没有使用或保留。正如已经指出的那样,问题在于 lambda 箭头 =&gt; 的左侧有 1 个参数,但您使用的委托需要 0 个参数。
  • 如果您将(例如)Action 更改为 Action&lt;object&gt;,则您的 RemoveReferenceExcecute 的签名将匹配,并且允许使用以下简单语法:command = new RelayCommand(RemoveReferenceExcecute);(通过“方法组" 转换)。
  • @hvd:你说得对,我没注意到这个。如果 RelayCommand 只有这一个构造函数,那么这肯定是问题所在 - (param) 不会匹配无参数的 Action

标签: c# lambda action


【解决方案1】:

System.Action 是无参数函数的委托。使用System.Action&lt;T&gt;

要解决此问题,请将您的 RelayAction 类替换为以下内容

class RelayAction<T> {
    readonly Action<T> _execute;
    public RelayCommand(Action<T> execute, Func<Boolean> canExecute){
        //your code here
    }
    // the rest of the class definition
}

注意RelayAction 类应该变成泛型。另一种方法是直接指定_execute 将接收的参数类型,但这样您将在使用RelayAction 类时受到限制。因此,在灵活性和稳健性之间存在一些折衷。

一些 MSDN 链接:

  1. System.Action
  2. System.Action&lt;T&gt;

【讨论】:

  • 如果是实现ICommand的类,这个类应该不是泛型的,委托类型应该是Action&lt;object&gt;,因为object是它的Execute方法传递的。
【解决方案2】:

您可以在不带任何参数的情况下定义命令“RemoveReferenceExcecute”

RelayCommand command = new RelayCommand(RemoveReferenceExcecute);}

或者您可以将一些参数/对象传递给它:

RelayCommand<object> command = new RelayCommand<object>((param)=> RemoveReferenceExcecute(param));}

在第二种情况下,不要忘记从您的视图中传递 CommandParameter;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-06-12
    • 2015-01-20
    • 1970-01-01
    • 1970-01-01
    • 2016-01-08
    • 2013-04-22
    相关资源
    最近更新 更多