Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/333.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 实体框架和大型查询。什么';它实用吗?_C#_Linq_Tsql_Entity Framework - Fatal编程技术网

C# 实体框架和大型查询。什么';它实用吗?

C# 实体框架和大型查询。什么';它实用吗?,c#,linq,tsql,entity-framework,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

我来自旧学校,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。它工作正常——我可以在profiler中看到它,但在IMO中它是不可维护的。另一个问题是,我正在进行投影并获取匿名对象。或者,我可以手动创建类并将其投影到该自定义类中

此时,我想知道在SQL Server上创建视图并将其添加到模型中是否更好?它将打破我的“客户端所有SQL”咒语,但更易于阅读和维护。没有

我想知道T-SQL和LINQ的较量从何而来

编辑

  • 型号说明。
  • 我有
    dsptruck
    DSPDrivers
    MBLDevices
  • 该设备可以连接到卡车或司机或两者
  • 我还有
    MBLPositions
    ,基本上是从设备ping(时间戳和GPS位置)
这个查询的作用是——它一次返回所有设备卡车司机信息,这样我就知道这个设备连接到了什么,它还得到了这些设备的最后一个GPS位置。答案可能是这样的:


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

您可以首先将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;
查询是延迟执行的,在编译它们或对它们进行迭代之前不会合成查询,所以您会在探查器中注意到这确实产生了一个有效的查询

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

一般来说,您的LINQ查询将比等效的SQL短,但我建议您尝试手动计算,而不是使用转换工具


除了CTE(我相当肯定你不能在LINQ中这样做)之外,我现在会在LINQ中编写所有查询

我发现,使用LINQ时,最好忽略它生成的任何sql,只要它检索正确的东西并且性能良好,只有当其中一个不起作用时,我才会真正查看它生成的内容

就其生成的sql是否可维护而言,您不必真正担心sql是否可维护,更不用担心生成sql的LINQ查询

最后,如果sql不太正确,我相信在某种程度上,您可以通过各种方法使LINQ生成的sql更符合您的要求


这样看来,取回匿名对象并没有任何固有的问题,但是如果您在多个地方执行此操作,您可能希望创建一个类来保持整洁。

一般来说,对于大多数简单的查询,我也默认使用LINQ


然而,当您遇到相应的LINQ查询变得更难编写和维护时,那么真正的问题是什么?所以我只想把这个问题留在原地。毕竟,它是有效的。为了便于使用,在EF模型中映射视图或存储过程非常简单。这没什么错,真的(IMO)。

我在所有方面都同意您的观点,但我只是不认为在LINQIn中执行查询时会更简单。我的LINQ使用连接和导航属性的变体。我喜欢这些东西。我只是不知道如何在LINQ中编写上述查询。你能试试吗?我想知道你是否会想出比generator更好的版本。在问题中张贴你的实际模型,以便我们可以看到更多信息以及查询实际试图实现的目标。在我的情况下,我不能使用anonymous。在Silverlight中,它们很难绑定(我没有提到),我正在使用DevForce,所以我必须创建类并使其可序列化,这样它就可以通过网络传输。我知道人们会不同意,我喜欢对象的LINQ,但说到SQL,我喜欢TSQL-Hints,#temp,行计数…让我切换到L2S的是当我看到生成sql时。与您的查询类似,生成的sql使用外部应用(选择TOP 1…)而不是内部连接SELECT MAX()。。。