实体框架和大型查询。什么是实用的?

时间:2011-12-22 23:08:22

标签: c# linq tsql entity-framework

我来自旧学校,DB将所有数据访问封装到视图,程序等中。现在我强迫自己使用LINQ来处理大多数明显的查询。

我想知道的是,什么时候停下来,什么是实用的?今天我需要像这样运行查询:

SELECT D.DeviceKey, D.DeviceId, DR.DriverId, TR.TruckId, LP.Description
FROM dbo.MBLDevice D
LEFT OUTER JOIN dbo.DSPDriver DR ON D.DeviceKey = DR.DeviceKey
LEFT OUTER JOIN dbo.DSPTruck TR ON D.DeviceKey = TR.DeviceKey
LEFT OUTER JOIN 
    (
    SELECT LastPositions.DeviceKey, P.Description, P.Latitude, P.Longitude, P.Speed, P.DeviceTime 
    FROM dbo.MBLPosition P
    INNER JOIN 
    (
        SELECT D.DeviceKey, MAX(P.PositionKey) LastPositionKey 
        FROM dbo.MBLPosition P
        INNER JOIN dbo.MBLDevice D ON P.DeviceKey = D.DeviceKey
        GROUP BY D.DeviceKey
    ) LastPositions ON P.PositionKey = LastPositions.LastPositionKey 
    ) LP ON D.DeviceKey = LP.DeviceKey
WHERE D.IsActive = 1

就个人而言,我无法编写相应的LINQ。所以,我在网上找到了工具并且回到了2页长的LINQ。它工作正常 - 我可以在分析器中看到它,但它不是可维护的IMO。另一个问题是我正在进行投影并获取Anonymous对象。或者,我可以手动创建类和项目到该自定义类。

此时我想知道在SQL Server上创建View并将其添加到我的模型中是否更好?它将破坏我的“所有SQL在cliens方面”的口头禅,但更容易阅读和维护。否?

我想知道你在哪里停止使用T-SQL和LINQ?

修改

  • 型号说明。
  • 我有DSPTrucksDSPDriversMBLDevices
  • 设备可以连接到卡车或司机或两者。
  • 我还有MBLPositions,它基本上是来自设备的ping(时间戳和GPS位置)

这个查询的作用 - 一次性它返回所有设备卡车司机信息,所以我知道这个设备连接到什么,它也是这些设备的最后GPS位置。回应可能如下:

enter image description here

有一些多余的东西,但没关系。我需要在一个查询中得到它。

3 个答案:

答案 0 :(得分:2)

一般情况下,对于大多数简单查询,我也会默认使用LINQ。

然而,当你遇到相应的LINQ查询变得难以编写和维护的那一点时,真正的重点是什么?所以我只是将该查询留在原地。毕竟它有用。为了更容易使用,可以非常简单地在EF模型中映射视图或 cough 存储过程。没错,真的(IMO)。

答案 1 :(得分:0)

您可以首先将Linq查询存储在变量中,这些变量可能有助于使其更具可读性,但也可以重复使用。

一个例子可能如下:

        var redCars = from c in cars
                      where c.Colour == "red"
                      select c;

        var redSportsCars = from c in redCars
                            where c.Type == "Sports"
                            select c;

查询是懒惰执行的,在编译它们或迭代它们之前不会编写,所以你会在profiler中注意到这确实产生了一个有效的查询

您还可以从定义模型中的关系和使用导航属性,而不是使用linq连接语法。这(再次)将使这些关系在查询之间可重用,并且更具可读性(因为您没有在查询中指定关系,如上面的SQL)

一般来说,你的LINQ查询会比同等的SQL短,但我建议尝试手工解决而不是使用转换工具。

除了CTE(我很确定你不能在LINQ中做)我会在LINQ编写所有查询

答案 2 :(得分:0)

我发现在使用LINQ时最好忽略它生成的任何sql,只要它检索正确的东西并且是高性能的,只有当其中一个不起作用时才真正看看它产生的是什么。

就它生成的可维护的sql而言,你不应该真的担心SQL是可维护的,而是更多的是生成SQL的LINQ查询。

最后,如果sql不太正确,我相信你可以采取各种措施让LINQ在某种程度上更多地生成SQL。

AFAIK回收匿名对象没有任何固有的问题,但是如果你这样做了多个地方你可能想创建一个类以保持整洁。