实体框架过滤嵌套类

时间:2017-06-28 20:23:36

标签: entity-framework linq

我的班级看起来像这样,

 public class Customer
 {
  public string id { get; set; }
  public string Name { get; set; }
  public List<Shop> Shops { get; set; }
 }

 public class Shop
 {
  public string FacilityType { get; set; }
  public Certifications ShopCertifications { get; set; }
 }

 public class Certifications
 {
  public bool M1002 { get; set; }
  public bool M1003 { get; set; }
 }

我有一份客户名单。例如,List<Customer> Entity = IfetchedFromMyDataBase;它看起来像这样,

 Entity[0]:
 {{"id":1,"Name":"Basanta",
    Shops[0]:{{"FacilityType":"MOB","ShopCertifications":null}}
    Shops[1]:{{"FacilityType":"BLAH","ShopCertifications":
                              {{"M1002":true,"M1003":false}}}}
 }}
 Entity[1]://So on

现在我想获取FacilityType = MOB的数据。因此,上述数据应该返回一个客户与一个商店。因为MOB只存在于一个商店中。

我使用了whereanyall。没有任何效果。甚至我的轰鸣声查询也不能仅过滤FacilityType。

Var Data = Entity.Where(m => m.Shops.Any(n => n.FacilityType == "MOB")).ToList();

甚至不是我的LINQ,

var data = (from d in Entity
            where (d.Shops.Any(x => x.FacilityType.ToUpper() == "MOB"))  
            select d);

当我查询上述内容时,都返回Customer with all the Shops. I mean one Customer two Shops, even it's FacilityType == "BLAH"。奇怪!

我在SO中几乎完成了与此相关的所有帖子。但没有运气。任何帮助,将不胜感激。

1 个答案:

答案 0 :(得分:1)

var data = (from d in Entity
            where (d.Shops.Any(x => x.FacilityType.ToUpper() == "MOB"))  
            select d);

这将返回包含&#34; MOB&#34;的所有客户。 facilityType。因此,如果客户包含一个&#34; MOB&#34;和&#34; BLAH&#34;然后该客户被退回。该客户的商店系列不会过滤到&#34; MOB&#34;商店。

如果您只想要拥有&#34; MOB&#34;以及他们的&#34; MOB&#34;商店..

var data = Entity
  .Where(d=> d.Shops.Any(x=> x.FacilityType.ToUpper() == "MOB"))
  .Select(x=> new { Facility = x, 
      MobShops = x.Shops
       .Where(s=> s.FacilityType.ToUpper() == "MOB")
       .ToList()})
  .ToList();

这将为您提供设施及其匹配商店列表的数据结构。

或者,如果您只对工厂感兴趣,然后解析其特定类型的商店,我会考虑向您的工厂实体添加帮助功能,以提供所需的商店过滤:< / p>

即。

public IEnumerable<Shop> ShopsOfType(string shopType)
{
  if (string.IsNullOrEmpty(shopType))
    return new List<Shop>(); // or null

  shopType = shopType.ToUpper();
  return Shops.Where(s=>s.FacilityType.ToUpper() == shopType).ToList();
}

这里要记住的事情: 如果返回客户(实体)的类似于存储库的方法返回List / IEnumerable,则您要么处理所有商店的急切加载,要么运行到延迟加载方案。我提倡的模式是让这些方法返回IQueryable,以便消费者可以在数据库上执行任何操作之前过滤数据。这样,像EF这样的ORM可以在没有显式包含的情况下计算其连接,并且您可以选择所需的相应数据(即填充视图模型等),而不是获取整个对象图。

考虑将FacilityType设为FK到具有数字Key列的查找表。这可以映射到代码或实体中的枚举。这避免了处理可能区分大小写的字符串并提高性能/ w索引的需要。