我有以下课程,例如
public class Team
{
[Key]
public virtual Int32 TeamId { get; set; }
[Required]
public virtual String Name { get; set; }
public virtual String Description { get; set; }
public virtual ICollection<TeamFeed> TeamFeeds { get; set; }
}
public class TeamFeed
{
public Int32 TeamFeedId { get; set; }
[Required]
public Int32 TeamId { get; set; }
public virtual bool IsEnabled { get; set; }
public virtual Team Team { get; set; }
}
我有LazyLoadingEnabled = false
和ProxyCreationEnabled = false
当我这样做时
var team = db.Teams.Where(x => x.TeamId == 1).Include(x=>x.TeamFeeds);
EF生成的SQL如下所示:
SELECT
[Project1].[TeamId] AS [TeamId],
[Project1].[Name] AS [Name],
[Project1].[Description] AS [Description],
[Project1].[C1] AS [C1],
[Project1].[TeamFeedId] AS [TeamFeedId],
[Project1].[TeamId1] AS [TeamId1],
[Project1].[IsEnabled] AS [IsEnabled],
FROM ( SELECT
[Extent1].[TeamId] AS [TeamId],
[Extent1].[Name] AS [Name],
[Extent1].[Description] AS [Description],
[Extent2].[TeamFeedId] AS [TeamFeedId],
[Extent2].[TeamId] AS [TeamId1],
[Extent2].[IsEnabled] AS [IsEnabled],
CASE WHEN ([Extent2].[TeamFeedId] IS NULL) THEN CAST(NULL AS int) ELSE 1 END AS [C1]
FROM [dbo].[Teams] AS [Extent1]
LEFT OUTER JOIN [dbo].[TeamFeeds] AS [Extent2] ON [Extent1].[TeamId] = [Extent2].[TeamId]
WHERE 1 = [Extent1].[TeamId]
) AS [Project1]
ORDER BY [Project1].[TeamId] ASC, [Project1].[C1] ASC
我不明白为什么它没有使用我会使用的SQL并创建了一个冗长的SQL语句。
SELECT
* --use all just for clarity in the example
FROM TEAMS T
INNER JOIN TEAMFEEDS TF
ON T.TEAMID = TF.TEAMID
ORDER BY
T.TEAMID
我是EF的新手,所以我可能不会理解某些事情。
由于
答案 0 :(得分:0)
首先,当INNER JOIN
的团队没有Feed时,使用TeamID = 1
的查询不会返回任何内容。这里必须使用LEFT JOIN
,这就是EF在ineer SELECT
中所做的事情:
SELECT
*
FROM [dbo].[Teams] AS [Extent1]
LEFT OUTER JOIN [dbo].[TeamFeeds] AS [Extent2] ON [Extent1].[TeamId] = [Extent2].[TeamId]
WHERE 1 = [Extent1].[TeamId]
关注可怕的行只是为了让EF知道,如果指定了JOIN
的左侧网站 - 如果团队没有Feed且0
则会返回1
如果找到了至少一个Feed。
CASE WHEN ([Extent2].[TeamFeedId] IS NULL) THEN CAST(NULL AS int) ELSE 1 END AS [C1]
外部SELECT
语句只是将DataBase列名称映射到EF模型属性名称,并ORDER BY
。
希望这足以说明为什么EF生成了这样的一个冗长的SQL语句。或者更确切地说,为什么这个陈述看起来很可怕,但实际上并不是简单的SELECT * FROM Teams JOIN Feeds
。