【问题标题】:Explain 2 pairs of parentheses in expression.Compile()()解释 expression.Compile()() 中的 2 对括号
【发布时间】:2018-01-03 13:07:47
【问题描述】:

你能解释一下这个奇怪的代码是做什么的吗?

expression.Compile()();

为什么这里有两对括号?我在谷歌没有找到任何东西。完整的方法是

public Validator NotEmpty(Expression<Func<IEnumerable<T>>> expression)
{
    var member = (MemberExpression)expression.Body;
    string propertyName = member.Member.Name;
    IEnumerable<T> value = expression.Compile()();

    if (value == null || !value.Any())
    {
        ValidationResult.AddError(propertyName, "Shouldn't be empty");
    }
    return this;
}

它是这样使用的:

_validator.NotEmpty(() => request.PersonIds);  // request.PersonIds is List<int>

此方法检查集合是否为空或 null。一切正常,但我对该代码有点困惑。我以前从未见过在 C# 中使用过 2 对括号。什么意思?

【问题讨论】:

  • 调用编译后的Func&lt;IEnumerable&lt;T&gt;&gt;表达式。
  • 仅供参考:第二对 ().Invoke(); 的简写,因此该行相当于:expression.Compile().Invoke();

标签: c# .net asp.net-web-api


【解决方案1】:

好吧,您将 int 列表作为表达式树传递给方法。此表达式生成 IEnumerable&lt;T&gt; 的值(在本例中为 IEnumerable&lt;int&gt;)。

要获取表达式的值,您需要将此表达式编译为委托Func&lt;IEnumerable&lt;T&gt;&gt;,然后调用该委托。 事实上,我可以编写两行单独的代码,而不是上面使用的较短的语法:

Func<IEnumerable<T>> del = expression.Compile();
IEnumerable<T> value = del();

【讨论】:

    【解决方案2】:

    两个括号()实际上是一个调用方法或委托的运算符。见here

    表达式“expression.Compile()”似乎传递了一个可以调用的委托。然后第二对括号调用此委托。

    你也可以这样改写:

    var del = expression.Compile();
    del();
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-08-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多