8

下面是一些 linqpad 测试代码。当它运行时会出错,因为“item”的第二个实例有一个空的子项目列表,而不是一个空列表。

我想以完全相同的方式处理这两种情况(空列表或空列表),但我想知道是否有比仅在列表上进行空检查并在有空时初始化空列表更简洁的方法。

换句话说,我可以这样做:

from si in (i.subitems == null ? new List<item>() : i.subitems)

但这有点难看,我想知道如何改进?

public class item
{
    public string itemname { get; set; }
    public List<item> subitems { get; set; }
}

void Main()
{
    List<item> myItemList = new List<item>() 
    {
        new item 
        {
            itemname = "item1",
            subitems = new List<item>()
            {
                new item { itemname = "subitem1" },
                new item { itemname = "subitem2" }
            }
        },
        new item 
        {
            itemname = "item2"
        }
    };

    myItemList.Dump();

    var res = (from i in myItemList
            from si in i.subitems
            select new {i.itemname, subitemname = si.itemname}).ToList();

    res.Dump();
}

作为一个额外的问题,这个相同的 linq 查询可以表示为 lambda 并以相同的方式处理空值吗?

干杯,克里斯

4

4 回答 4

15

您可以使用空合并运算符

var res = (from i in myItemList
           from si in i.subitems ?? new List<item>()
           select new { i.itemname, subitemname = si.itemname }).ToList();

但我认为你应该把空的过滤掉

var res = (from i in myItemList
           where i.subitems != null
           from si in i.subitems
           select new { i.itemname, subitemname = si.itemname }).ToList();

至于 lambda 版本,您可以说

var res = myItemList.Where(x => x.subitems != null)
                    .SelectMany(
                        x => x.subitems.Select(
                            y => new { x.itemname, subitemname = y.itemname }
                        )
                     );

但是查询语法版本更具可读性。

于 2010-02-04T17:52:42.047 回答
12
from si in (i.subitems ?? new List<item>())

那个怎么样?

于 2010-02-04T17:48:08.937 回答
10

您可以添加一个(邪恶的)扩展方法来为您完成工作

public static IEnumerable<T> EnsureNotEmpty<T>(this IEnumerable<T> enumerable) {
  if ( enumerable == null ) {
    return Enumerable.Empty<T>();
  } else { 
    return enumerable;
  }
}
于 2010-02-04T17:49:03.727 回答
0

另一种方法是不允许子项为空。您可以制作项目构造函数,以便将子项目默认为空列表,然后在子项目设置器中不允许 null 。

这当然假设您有权修改项目。

正如 Hunter Daley 所指出的,您正在寻找空合并运算符

于 2010-02-04T17:54:01.183 回答