收益率内部使用率
|
如果我没记错的话,当我在
using SqlConnection
块内使用yield时,我会遇到运行时异常。
using (var connection = new SqlConnection(connectionString))
{
var command = new SqlCommand(queryString, connection);
connection.Open();
SqlDataReader reader = command.ExecuteReader();
// Call Read before accessing data.
while (reader.Read())
{
yield reader[0];
}
// Call Close when done reading.
reader.Close();
}
当我用一个List替换yield
时解决了这些问题,每次迭代都添加了项。
在using StreamReader
街区中时,我还没有发生相同的问题
using (var streamReader = new StreamReader(fileName))
{
string line;
while ((line = streamReader.ReadLine()) != null)
{
yield return line;
}
}
有什么解释为什么在前一种情况下而不是在后一种情况下发生异常?这是明智的选择吗?
编辑要获取我过去所做的错误(及早处置),您应该调用以下第一个方法:
IEnumerable<string> Read(string fileName)
{
using (var streamReader = new StreamReader(fileName))
{
return Read(streamReader);
} // Dispose will be executed before ReadLine() because of deffered execution
}
IEnumerable<string> Read(StreamReader streamReader)
{
string line;
while ((line = streamReader.ReadLine()) != null)
{
yield return line;
}
}
可以通过其他推迟执行的方式来实现相同的错误,例如“ 6”
没有找到相关结果
已邀请:
2 个回复
茶鬼失形
问题的详细说明,请参见这篇文章。因为返回枚举数,所以using块在访问任何内容之前已经破坏了上下文。答案有很好的解决方案,基本上,可以将wrapper方法用作枚举器,或者构建一个列表。 另外,通常在阅读器周围放置ѭ7(而不是连接),并使用ѭ10来确保阅读器完成后释放资源,通常更为实用。尽管在您的情况下并不重要,但是如果您曾经从方法中返回数据读取器,这将确保在处理读取器时正确关闭连接。
寇剩
块内的
。没有明显的理由应该引发异常。 要注意的一件事是,只有在完成迭代和/或手动布置枚举器对象后,才会释放该连接。如果您以公共方法公开此代码,那么愚蠢或恶意的代码很可能会使您的连接长时间保持打开状态: