检索大型记录集时 DataReader 挂起

Posted

技术标签:

【中文标题】检索大型记录集时 DataReader 挂起【英文标题】:DataReader Hanging when retrieving large recordset 【发布时间】:2014-02-24 19:04:48 【问题描述】:

我目前的情况是我有一个非常大的记录集(大约 200 万条记录)我正在尝试使用 .Net 和 Oracle.DataAccess.dll 库(版本 2.112.2.0)从 oracle 数据库中查询。

Imports Oracle.DataAccess.Client
Imports Oracle.DataAccess

...在我的程序中:

Dim conn As New OracleConnection()

   ... connect to DB, etc (this all works fine) ...

Dim strSQLQuery = (Query for large recordset)
Dim cmd = New OracleCommand(strSQLQuery, conn)

   Using Reader As OracleDataReader = cmd.ExecuteReader()
    ...
   End Using

现在,此过程适用于较小的查询,但对于这个大型查询,它似乎无限期挂起(我已经等了一夜,然后最终退出程序)在 Using.. 行上,甚至没有进入 using 语句中的代码行......它似乎根本没有做任何事情。

起初,我认为这可能是我的查询本身的问题,但是当我尝试使用 SQL Navigator 运行它时,它会在不到 10 分钟内返回记录集...

我做错了吗?这是正常的吗?我可以设置一个设置来使OracleDataReader 不挂起吗?

此外,即使这段代码是用 VB 编写的,我对 C# 也同样满意。

【问题讨论】:

SQL Navigator 是否真的返回所有值?他们可能会包装你的 sql 语句,只得到前 100 个结果之类的东西。 它返回前250,然后您可以单击以继续获取越来越多...如果我选择将其下载到分隔的文本文件中,需要一段时间,但它会减少超过 30 分钟左右... 也许您机器上的网络缓冲区已满?如果是这样,也许您可​​以简单地将查询分解为多个较小的查询? 网络缓冲区是数据保存的地方,直到您开始读取它。msdn.microsoft.com/en-us/library/ms254931(v=vs.110).aspx 感谢@smoore,我尝试将其分解为较小的查询,但它仍然挂起......也许我需要进一步分解它......有什么办法可以强制网络缓冲区,一旦达到该大小,启动数据读取器,然后刷新它并获取更多数据或您知道的类似数据?? 【参考方案1】:

如果您尝试在不使用 using 语句的情况下创建阅读器,这听起来可能很愚蠢。在工作中,他们建议不要使用“使用”,因为当我们使用使用时,我们已经看到大量数据会发生不好的事情。因此,作为最佳实践,我们只需在新过程中创建阅读器,使其范围在过程结束时结束。

【讨论】:

非常有趣!! - 我从来没有尝试过...我目前没有遇到这个问题,但下次我会尝试,如果它有效,我会HAPPILY将此标记为解决方案...感谢您的想法。从来没有想过尝试这样做。

以上是关于检索大型记录集时 DataReader 挂起的主要内容,如果未能解决你的问题,请参考以下文章

SQL Server锁定的DataReader行为

检索包含 CLUB 的 100 行后程序仍然挂起

.Net 中 Oracle DataReader 的大性能问题

什么会导致 OdbcDataReader 挂起?

使用 DataReader 将数据库多条记录存储到变量中

Spark 2.1 在读取大量数据集时挂起