【问题标题】:Declaring navigation property as lazy loading but eager loading it. Bad practice?将导航属性声明为延迟加载但急切加载它。不好的做法?
【发布时间】:2014-01-30 22:13:40
【问题描述】:

我们所有的导航属性都被定义为虚拟的(延迟加载),但其中大部分是预先加载的(.Include)。延迟加载的灵活性是否会影响性能?我们应该只在真正需要延迟加载时才延迟加载吗?

谢谢。

【问题讨论】:

    标签: c# performance entity-framework lazy-loading eager-loading


    【解决方案1】:

    快速基准测试(在对象图中加载数千个对象)表明,启用或禁用延迟加载和代理生成时,加载时间没有明显差异。

    但是,当您知道自己进行了预加载(并且可能使用了短暂的上下文)时,我总是会关闭延迟加载和代理生成。

    context.Configuration.LazyLoadingEnabled = false;
    context.Configuration.ProxyCreationEnabled = false;
    

    尽管它没有显着提高性能,但至少它消除了在上下文超出范围时触发延迟加载或在对象被序列化时触发延迟加载级联的风险。

    在您的情况下,当急切加载盛行时,您甚至可以将其设为默认值,即在您的上下文类的构造函数中打开这些属性。

    请注意,当您使用 AsNoTracking() 获取对象时,确实会提高性能,当您获取用于只读目的的对象时,这是一种很好的做法。这种情况经常发生:在断开连接的设置中,例如当对象被序列化到 Web 客户端时,上传始终是只读的,即使客户端可能能够修改对象。更改在 post 操作中处理。

    【讨论】:

      【解决方案2】:

      这取决于您为什么要处理返回的对象。当您尝试访问导航属性时,延迟加载会导致将新查询发送到数据库。

      如果您急切地加载对象以包含它的所有导航属性,然后从不使用它们,它们是的。您正在从数据库请求更多数据,然后必须花费更多时间来解析它们。当然反过来也一样。

      如果您从数据库中获取一个对象并开始访问导航属性,您必须在数据库中查询它们,从而导致发生 n+1 个查询。我会说这比批量查询记录成本更高,但实际上取决于您知道对象将如何用于特定操作。

      就个人而言,在网络环境中,我渴望加载,因为上下文是短暂的。在桌面环境中,您要为整个应用程序会话保持上下文活动,我会使用延迟加载,因为您不必为后续查询一遍又一遍地构建上下文。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-09-30
        • 1970-01-01
        相关资源
        最近更新 更多