在SQLDataReader上使用

我知道我之前提过了一个相关的问题。 我只是想到了另一个想法。

using (SqlConnection conn = new SqlConnection('blah blah')) { using(SqlCommand cmd = new SqlCommand(sqlStatement, conn)) { conn.open(); // *** do I need to put this in using as well? *** SqlDataReader dr = cmd.ExecuteReader() { While(dr.Read()) { //read here } } } } 

这个论点是:由于SqlDataReader dr对象不是一个新的OBJECT LIKE连接或命令对象,它只是一个指向cmd.ExecuteReader()方法的引用,我是否需要将阅读器放在一个using 。 (现在基于我以前的post,我的理解是任何使用IDisposable对象都需要放入using ,而SQLDataReaderinheritance自IDisposable ,所以我需要把它放进去。我的判断是否正确?)我只是因为它不是一个新对象,所以它会在处理一个只是指向命令的引用指针的对象时引起任何问题吗?

非常感谢

我觉得你错了。 dr是对cmd.ExecuteReader返回的对象的cmd.ExecuteReader ,它将成为一个新对象。 在你的例子中,什么都不会处理dr ,所以是的,它需要在using ,或手动处置。

您对IDisposable实现者需要 using判断不正确。 他们在外面运作良好。 一个using语句只是一个try ... finally语法糖try ... finally 。 实现IDisposable事情应该让Dispose调用,因为它们表明他们需要以确定的方式处理某些状态。

请注意,如果您不调用Dispose ,它并不总是一个问题。 一些对象还实现了终结器,它将由垃圾收集器触发。 如果他们没有实现终结器,他们可能会使未管理的内存无法恢复。 在您的申请结束之前,这将一直无法恢复。 所有托管内存最终都会被回收,除非它不适合垃圾回收。

重新编写:

 using (SqlConnection conn = new SqlConnection('blah blah')) using(SqlCommand cmd = new SqlCommand(sqlStatement, conn)) { conn.open(); using (SqlDataReader dr = cmd.ExecuteReader()) { while (dr.Read()) { //read here } } } 

您应该将数据读取器包装在using语句中,因为ExecuteReader方法正在创建一个也应该被丢弃的新数据读取器实例。