【问题标题】:Why is Null an Invalid LINQ projection?为什么 Null 是无效的 LINQ 投影?
【发布时间】:2010-09-22 11:22:01
【问题描述】:

我有以下语句,它总是返回 null:

var addins = allocations.SelectMany(
        set => set.locations.Any(q => q.IsMatch(level, count))
        ? (List<string>)set.addins : null
     );

我稍微改了一下,现在可以正常使用了:

var addins = allocations.SelectMany(
        set => set.locations.Any(q => q.IsMatch(level, count))
        ? set.addins : new List<string>()
     );

我的主要问题:为什么在这种 LINQ 上下文中 null 不能作为三元运算符的返回类型?

第二个问题:是否有更聪明的方法来制定上述查询(特别是如果它消除了“new List()”)?

【问题讨论】:

    标签: c# linq


    【解决方案1】:

    Enumerable.SelectMany 将尝试枚举您的 lambda 返回的序列,并抛出 NullReferenceException 尝试在 null 上调用 GetEnumerator()。您需要提供一个实际的空序列。您可以使用Enumerable.Empty,而不是创建一个新列表:

    var addins = allocations.SelectMany(
        set => set.locations.Any(q => q.IsMatch(level, count))
        ? (List<string>)set.addins : Enumerable.Empty<string>()
        );
    

    我怀疑你真正想要的只是在 SelectMany 之前调用 Where 来过滤掉你不想要的集合:

    var addins = allocations
        .Where(set => set.locations.Any(q => q.IsMatch(level, count)))
        .SelectMany(set => (List<string>)set.addins);
    

    或者,在查询语法中:

    var addins =
        from set in allocations
        where set.locations.Any(q => q.IsMatch(level, count))
        from addin in (List<string>)set.addins
        select addin;
    

    【讨论】:

    • 出色的答案和见解。顺便说一句,在您的其他示例中,不需要对“set.addins”进行强制转换,因为不涉及三元运算符。
    【解决方案2】:

    做到这一点:

    (List&lt;string&gt;)set.addins : (List&lt;string&gt;)null

    【讨论】:

      猜你喜欢
      • 2014-06-08
      • 1970-01-01
      • 1970-01-01
      • 2019-07-09
      • 2017-02-15
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-05-15
      相关资源
      最近更新 更多