【发布时间】:2010-11-23 08:51:39
【问题描述】:
如果可以的话,请提供建议......
我的项目基于 Linq-To-SQL,并且(几乎)完成的应用程序的性能非常差。我已经多次启动 SQL Profiler 以使用 LoadOptions 优化查询以减少到数据库服务器的往返次数,但归根结底,我的难题被编织成以下几点:
Microsoft 的官方建议是 DataContext 应该不有很长的生命周期 - 也就是说 - 他们建议您创建 DataContext、物化对象、进行更改、调用 SubmitChanges() ,然后处置。我的应用程序虔诚地遵循这种模式。
DataContext 往往非常粘着它的实体,在更改跟踪和延迟关系加载重新连接的对象。因此,保持加载的对象缓存已被证明是有问题的。
当在 DataContext 上设置 LoadOptions 以加载多层关系时,性能会受到影响,因为生成的数据是相关行的乘积,而不是它们的总和。我从字面上提取数据的特定模式导致设置 LoadOptions 时返回的数据量增加了 144 倍,因此自然而然地这最终成为性能杀手,而不是帮助者。
如果未设置 LoadOptions(或者即使将其设置为降低的级别),DataContext 会执行数百次到数据库的往返。
我还注意到 DataContext 忽略了在第一次通过关系访问对象时已经加载了对象...例如:
Dim allCustomers as Customers() = Context.Customers.ToArray()
Dim allOrders as Orders() = Context.Orders.ToArray()
For Each o as Order in allOrders
Console.WriteLine(o.Customer.Name) ' <- Triggers round-trips to database!!!
Next
总之,我遇到的问题是我的客户无法接受我所获得的性能,并且:
- 不建议保留单个应用程序范围的 DataContext。
- 缓存和重新附加实体(似乎)存在问题。
- DataContext.LoadOptions 具有深度、多层次的关系,会损害性能
- 预加载整个表的数据没有帮助 - 访问外键关系时,DataContext 仍会刷新加载的对象。
我真的觉得我在这里遗漏了一些基本的东西,也许是在我采用的整体设计模式中,并且如果你有任何关于从 DataContext 中获取加载的 Object-Graph 而没有所有往返或臃肿的网络流量。
你的建议?
【问题讨论】: