【问题标题】:Modify Linq query to support optional relationships修改 Linq 查询以支持可选关系
【发布时间】:2014-03-18 12:22:43
【问题描述】:

我遇到了一个连接记录为空的 linq 查询问题。

我有 3 个模型:

地点、公司和人员。

  • 一个人必须在一家公司工作
  • 一个人可能只有一个位置
  • 一个公司可能有多个人

我正在使用以下 LINQ 查询来检索特定公司所有人员的所有位置的不同列表:

locations =
            db.Companies.Where(c => c.Name == company.Name)
            .SelectMany(c => c.People)
            .Select(p => p.Location)
            .Distinct()
            .ToList();

如果从此查询中检索到的 Peron 没有位置(位置对于人员来说是可选的),就会出现问题。

在这种情况下,以下获取每个位置名称的查询由于未将对象引用设置为对象而失败:

locations.Select(g => g.Name).ToList()

如何更改上述行以忽略检索到的人员记录没有位置的记录?

【问题讨论】:

  • 当你说一个Person没有位置的时候,你的意思是这个属性是null,还是一个空字符串?
  • 抱歉,应该澄清一下 - 空

标签: c# linq


【解决方案1】:

试试这个:

locations =
            db.Companies.Where(c => c.Name == company.Name)
            .SelectMany(c => c.People)
            .Where(p => p.Location !=null)
            .Select(p => p.Location)
            .Distinct()
            .ToList();

干杯

【讨论】:

    【解决方案2】:

    通常,您可以使用空值合并或条件运算符来检查空值,然后将其替换为合适的默认值,例如:

    locations =
            db.Companies.Where(c => c.Name == company.Name)
            .SelectMany(c => c.People)
            .Select(p => p.Location ?? SomeDefaultLocation)
            .Distinct()
            .ToList();
    

    例如SomeDefaultLocation 可以是 readonly staticLocation 实例。

    但是,在您提供的上下文中,这实际上没有意义(例如,所有没有位置的人都会返回 SomeDefaultLocation)。这将是更典型的用法:

    personAndLocations =
            db.Companies.Where(c => c.Name == company.Name)
            .SelectMany(c => c.People)
            .Select(p => new 
              {Person = p, 
               Location = p.Location ?? SomeDefaultLocation})
            .ToList();
    

    【讨论】:

    • 感谢您使用空合并运算符,这是一个很好的例子,尽管我已将 @Luc Morins 标记为答案,因为它更符合我的要求
    猜你喜欢
    • 2013-01-21
    • 1970-01-01
    • 2010-09-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-01-30
    • 1970-01-01
    相关资源
    最近更新 更多