【问题标题】:How To use Contains in left outer Join Linq如何在左外加入 Linq 中使用包含
【发布时间】:2017-09-13 13:07:21
【问题描述】:

我有这个查询

          from Room in PMSdb.Room_Tbl
                join Res in PMSdb.Reservation_Tbl on
                Room.Room_ID equals Res.Room_ID
                into ej
                from Res in ej.DefaultIfEmpty() 
                join Feature in PMSdb.Room_Features_Tbl on
                Room.Room_Features.Split(',').Contains(Feature.Room_Features_ID.ToString())
                into FE
                from Feature in FE.DefaultIfEmpty()
                  select new
                              {
                                  Room = Room.Room_Number,
                                  Room_type = RoomType.Room_Type_Code
                                  Feature =Feature.Feature_Name}

我需要这样做 Room.Room_Features.Split(',').Contains(Feature.Room_Features_ID.ToString()) 但它拒绝 我该怎么做?

【问题讨论】:

  • 那么Room_Features 是逗号分隔的功能列表吗?如果是这样,简短的回答是“不要那样做”。相反,您应该有一个 RoomFeatures 表,它有两列(Room_ID 和 Feature_ID),这样您就可以在 Room 和 Feature 之间建立多对多关系。
  • @GertArnold 如您所说,如何首先创建变量?因为我没有它,它是动态的
  • linq-to-sql / entity-framework - 是哪一个?
  • 是的,但是为什么呢?这是一个糟糕的设计。 RoomFeatures 应该是一个单独的表。
  • 您可能只需要获取数据到客户端并在那里运行 String.Split,然后在客户端上执行其余的逻辑。

标签: c# entity-framework linq linq-to-sql


【解决方案1】:

您真的应该考虑使用联结表来规范化该数据,逗号分隔的字段是不良数据库设计的标志。

话虽如此,问题在于实体框架无法将string.Split() 转换为 SQL 查询。

如果您的数据存储为,val1,val2,,val3,(前缀和后缀都带有逗号,而逗号不是有效值),您可以使用string.Contains可以翻译到 SQL:

Room.Room_Features.Contains($",{Feature.Room_Features_ID},")

【讨论】:

  • OP 可能没有更改现有数据库的选项,因此您的建议是无用的。
  • @jdweng 对你的复仇投反对票。正如How to Answer 中所解释的那样,多人多次向您解释“试试这个[代码块]”不是一个好的答案。除此之外,我的答案确实包含一个不需要更改数据库结构的解决方案,请尝试阅读第一句话之外的内容。
【解决方案2】:

这个怎么样:

(from Room in PMSdb.Room_Tbl
            join Res in PMSdb.Reservation_Tbl on
            Room.Room_ID equals Res.Room_ID
            into ej
            from Res in ej.DefaultIfEmpty()
            select new { room = Room, res = Res)
            .Where(x => x.Res == null)
            .Select(x => new {
                             Room = x.room.Room_Number,
                             Room_type = x.room.Room_Type_Code,
                             Features = x.room.Room_Features.Split(new char[] {','})
                                .Select(y => PMSdb.Room_Features_Tbl.Where(z => z.Room_Features_ID.ToString() == y.Trim()).FirstOrDefault())
                                .ToList() 
            }).ToList();

【讨论】:

  • Contains 发生了什么?这在逻辑上是不同的。 EF6 不接受String.Split。不幸的是,OP 没有告诉他们实际使用的是哪个 ORM。
  • @JdWeng Room_Feature 表在哪里?我想从中选择
  • 它不是 PMSdb.Room_Tbl 中的房间的一部分吗?
  • 不要回答“试试这个[代码块]”,而是尝试解释 OP 有什么问题,你为了规避这个问题而做了什么改变,以及它是如何解决上述问题的。
  • 每个人都从解释中受益。阅读my answer in "What should a minimal answer contain?"。我们不只是为 OP 发布答案,而是为每个在他们之后阅读 Q&A 的人发布答案。如果所有答案都采用您通常使用的形式,我们将拥有一个充满“试试这个 [代码块]”答案的网站,那么 Google 员工需要做什么?从所有答案中复制粘贴代码?阅读每一行代码,尝试猜测你在编写它时的想法?如果您的假设或实施有误怎么办? @David 我经常告诉你。
猜你喜欢
  • 1970-01-01
  • 2021-12-11
  • 2015-03-06
  • 2010-12-29
  • 2016-02-05
  • 1970-01-01
  • 2012-04-19
  • 2018-02-10
  • 2011-11-13
相关资源
最近更新 更多