【问题标题】:How to access associations in a LINQ query?如何访问 LINQ 查询中的关联?
【发布时间】:2011-07-19 15:25:44
【问题描述】:

我在查询这个问题时遇到了问题(我是 LINQ 的新手,请原谅我),我已经花了几个小时在网上搜索。在 SQL 中我只想这样做

SELECT c.Forname, c.Surname cg.Title, g.GroupName
FROM Contact c
    inner join ContactGroup cg on cg.ContactID = c.ID
    inner join Group g on cg.GroupNameID = g.ID
WHERE g.ID=1;

我尝试过,但失败了:

var result = 
    from c in cc.Contacts
    from cg in c.ContactGroups
    from g in cg.Group 
    where g.ID==1
    select new
    {
        c.Forename,
        c.Surname,
        cg.Title,
        g.GroupName
    };

谁能告诉我我做错了什么或将我引导到某个地方以提供更多信息?

非常感谢。

【问题讨论】:

  • 您遇到什么错误? IntelliSense 应该能够告诉您变量的类型,并且您应该能够从那里找出它
  • gc.Title 应该是 cg.Title。我改了,以为是错字。
  • 您的查询结果不满意的原因是什么?它不编译吗?它会给出错误信息吗?乍一看,我觉得很合适。
  • 在这种情况下不需要打开(和关闭),但除此之外它看起来不错。当然,在您遍历结果之前,它不会对数据库执行实际查询(可能通过调用 ToList() 之类的简单操作。您需要提供更多关于哪些不起作用的细节。跨度>

标签: c# linq ado.net-entity-data-model


【解决方案1】:

我会稍微改变一下,然后使用ContactGroup 表开始您的查询。这样您就可以“访问”所有 3 个表。

from c in cc.ContactGroups
where c.GroupNameID == 1
select new {
    c.Contact.Forename,
    c.Contact.Surname, 
    c.Title,
    c.Group.GroupName
}

这是在Linqpad 中生成的SQL(使用Linq to Sql,但EF 不会有太大不同)- 几乎与您的查询完全一样。

-- Region Parameters
DECLARE @p0 Int = 1
-- EndRegion
SELECT [t1].[Forename], [t1].[Surname], [t0].[Title], [t2].[GroupName]
FROM [ContactGroups] AS [t0]
INNER JOIN [Contacts] AS [t1] ON [t1].[ID] = [t0].[ContactID]
INNER JOIN [Groups] AS [t2] ON [t2].[ID] = [t0].[GroupNameID]
WHERE [t0].[GroupNameID] = @p0

【讨论】:

  • 谢谢!这是“正确”的做法还是偷偷摸摸的方式? :)
  • @Ichirichi - 我认为这是正确的方法。它肯定会产生“正确的”sql。我没有过多使用 EF,但我相信 EF4 已经内置了对 many-to-many 关系的支持(不确定它是否在早期版本中),您可以在其中取消连接表 - 但前提是连接表没有任何除了外键之外的其他列。 Linq to Sql 没有这种支持,所以这个解决方案是最简单的方法。
【解决方案2】:

在 linq 中,你的连接看起来像这样

from c in cc.Contacts
join cg in c.ContactGroups on cg.Id equals c.Id

看这里:http://www.dotnetperls.com/join

【讨论】:

  • 不太正确,因为他没有直接从上下文中加入 ContactGroups。 c.ContactGroups 已经自动加入。
  • 你不应该加入它,因为关系应该已经在模型中定义了。
  • 确实如此。取决于延迟加载/急切加载..他也可以做​​ cc.Contacts.Include("")... 对吗?
  • 延迟/急切加载仅适用于未在 select 语句中选择的实体。如果您将导航属性作为 LINQ 语句的一部分进行遍历,并选择所有您需要选择的内容,EF 将加载您所要求的内容。延迟/急切加载仅适用于在 select 语句中选择了一个完整实体并且它具有您也想要但未明确选择的其他导航属性的情况。
【解决方案3】:

我个人认为LINQPad 是学习一般 LINQ 和 LINQ-to-SQL 的好资源。也许对你有帮助。

【讨论】:

    【解决方案4】:
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-01-27
    • 1970-01-01
    • 1970-01-01
    • 2013-06-07
    相关资源
    最近更新 更多