Asp.net mvc 在实体框架中使用语句

Asp.net mvc 在实体框架中使用语句,asp.net-mvc,entity-framework,Asp.net Mvc,Entity Framework,我想问一下实体框架中的“使用”语句。正如我在其他论坛和书籍中多次看到的,使用以下代码(来自ASP.NET MVC4应用程序)查询数据库是一种很好的做法: 但另一方面,若我们使用脚手架来生成控件器方法和视图,那个么默认生成器将声明 private ProductsEntites db = new ProductsEntites() 在控制器级别,因此在本例中,用于存储查询结果的内存仅在超时使用过期时释放,垃圾收集器将解锁内存以满足其他需要。那么,什么对小型网站更好,什么对大型网站最好呢?即使您不

我想问一下实体框架中的“使用”语句。正如我在其他论坛和书籍中多次看到的,使用以下代码(来自ASP.NET MVC4应用程序)查询数据库是一种很好的做法:

但另一方面,若我们使用脚手架来生成控件器方法和视图,那个么默认生成器将声明

private ProductsEntites db = new ProductsEntites()

在控制器级别,因此在本例中,用于存储查询结果的内存仅在超时使用过期时释放,垃圾收集器将解锁内存以满足其他需要。那么,什么对小型网站更好,什么对大型网站最好呢?

即使您不调用Dispose方法,Entity Framework开发者也可以很好地工作(当您使用
使用
语句时,您是隐式调用Dispose方法)

它工作得很好,因为EF使用了一种称为Fly-Weight的设计模式。本质上,一段数据始终保留在内存中。这是因为EF在服务器的第一次执行中有延迟,并且当您终止应用程序时有延迟


因此,您可以使用类似于脚手架模板的代码,而无需担心。

您可以覆盖控制器的
Dispose
方法。应该在请求结束时调用它

    protected override void Dispose(bool disposing) {
        if(disposing)
            db.Dispose();
    }

小心使用EF语句,确保通过使用ToList或ToArray等将所有IQueryable回报转换为IEnumerable,从而实现所有IQueryable回报

如果不这样做,延迟加载可以尝试访问上下文,以便在使用某些导航属性时获取这些属性,如果上下文被释放,则会引发异常。

private ProductsEntites db = new ProductsEntites()
作为一个类变量,在controllers Dispose方法中进行Dispose对我来说很好。正如穆罕默德·阿塔什指出的那样:

protected override void Dispose(bool disposing) {
    if(disposing)
        db.Dispose();
}

控制器在执行操作后被释放。

这不是using语句的问题,这是EF的一般问题。即使没有using语句,同样的问题也可能发生,因为上下文可以在控制器被释放后的任何时间被释放。对IQueryable的任何引用都可能引发相同的异常。诚然,这不太可能在单个请求的空间中发生,但这是可能的。using语句只会让它发生得更快。我总是在Julie Lermann和其他专家的建议下调用.ToList()。我只想知道您使用的是哪种方法-默认值是由scaffolding生成的,还是在每个操作中显式调用“using”语句?它已经在这里了,默认情况下生成了以下代码:protectedoverrideviddispose(bool disposing){db.Dispose();base.Dispose(disposing);}我只是关心内存使用情况,如果100000个用户会来:)这是我以前错过/不理解的:“控制器在执行操作后被释放。”感谢澄清为什么我们需要释放它,尽管我们正在使用“使用”语句?我不明白,我一直以为“使用”会自己解决的。谢谢你的提示,帮我解决了一个问题。
protected override void Dispose(bool disposing) {
    if(disposing)
        db.Dispose();
}