【发布时间】:2019-01-10 11:26:05
【问题描述】:
我有一个用于替换数据库函数的 Linq 查询。这是第一个有多个连接的,我似乎无法弄清楚为什么它返回 0 个结果。
如果您发现任何可能导致错误返回的差异,我们将不胜感激......我一直在努力解决这个问题。
Linq 查询
context.StorageAreaRacks
.Join(context.StorageAreas, sar => sar.StorageAreaId, sa => sa.Id, (sar, sa) => new { sar, sa })
.Join(context.StorageAreaTypes, xsar => xsar.sar.StorageAreaId, sat => sat.Id, (xsar, sat) => new { xsar, sat })
.Join(context.Racks, xxsar => xxsar.xsar.sar.RackId, r => r.Id, (xxsar, r) => new { xxsar, r })
.Where(x => x.xxsar.sat.IsManual == false)
.Where(x => x.r.IsEnabled == true)
.Where(x => x.r.IsVirtual == false)
.Select(x => new { x.xxsar.sat.Id, x.xxsar.sat.Name })
.Distinct()
.ToList();
这是由 LINQ 查询生成的查询
SELECT
[Distinct1].[C1] AS [C1],
[Distinct1].[Id] AS [Id],
[Distinct1].[Name] AS [Name]
FROM ( SELECT DISTINCT
[Extent2].[Id] AS [Id],
[Extent2].[Name] AS [Name],
1 AS [C1]
FROM [dbo].[StorageAreaRacks] AS [Extent1]
INNER JOIN [dbo].[StorageAreaTypes] AS [Extent2] ON [Extent1].[StorageAreaId] = [Extent2].[Id]
INNER JOIN [dbo].[Racks] AS [Extent3] ON [Extent1].[RackId] = [Extent3].[Id]
WHERE (0 = [Extent2].[IsManual]) AND (1 = [Extent3].[IsEnabled]) AND (0 = [Extent3].[IsVirtual])
) AS [Distinct1]
产生所需结果的Sql Query
SELECT DISTINCT sat.Name, sat.Id
FROM StorageAreaRacks sar
JOIN StorageAreas sa on sa.id = sar.StorageAreaId
JOIN StorageAreaTypes sat on sat.id = sa.StorageAreaTypeId
JOIN Racks r on r.id = sar.RackId
WHERE sat.IsManual = 0
AND r.IsEnabled = 1
AND r.IsVirtual = 0
【问题讨论】:
-
使用什么 ORM 来运行此查询(EF6、EF Core 等)?生成的 SQL 是什么?
-
@IvanStoev ORM 是 EF6,我不得不查找如何查看生成的 SQL 查询。这对我来说是新事物,因此经历可能会有所帮助。由于太长,我将生成的查询添加到问题中。
-
嗯,在 EF6 中,您可以简单地将
.ToList()替换为.ToString(),然后您将获得 SQL 查询 :) -
@IvanStoev EF 和 LINQ 对我来说很陌生,所以我还有很多东西要学:P。
-
请使用导航属性重写此 LINQ 查询。连接很冗长(尤其是在方法语法中)并且很容易出错。例如,
StorageAreaTypes不应与StorageAreaId连接。使用导航属性时,连接字段不可能不匹配。
标签: c# entity-framework linq join entity-framework-6