在我的java代码中,我使用select语句访问oracle数据库表。
我收到很多行(大约50.000行),因此rs.next()
需要一些时间来处理所有行。
using ResultSet, the processing of all rows (rs.next) takes about 30 secs
我的目标是加快这个过程,所以我更改了代码,现在使用CachedRowSet
:
using CachedRowSet, the processing of all rows takes about 35 secs
我不明白为什么CachedRowSet
比正常ResultSet
慢,因为CachedRowSet
一次检索所有数据,而ResultSet
每次检索数据调用rs.next
的时间。
以下是代码的一部分:
try {
stmt = masterCon.prepareStatement(sql);
rs = stmt.executeQuery();
CachedRowSet crset = new CachedRowSetImpl();
crset.populate(rs);
while (rs.next()) {
int countStar = iterRs.getInt("COUNT");
...
}
} finally {
//cleanup
}
答案 0 :(得分:4)
CachedRowSet将结果缓存在内存中,即您不再需要连接。因此它更慢"首先。
CachedRowSet对象是用于缓存其数据的数据行的容器 内存中的行,这使得可以不经常操作 连接到其数据源。
- > http://download.oracle.com/javase/1,5.0/docs/api/javax/sql/rowset/CachedRowSet.html
答案 1 :(得分:4)
CachedRowSet
与postgres jdbc驱动程序一起出现问题。
CachedRowSet
需要知道列的类型,以便知道要创建哪些java对象
(上帝知道它从封面后面的DB中取出了什么!)。
因此,它会向DB进行更多往返以获取列元数据。 在非常大的量中,这成为一个真正的问题。 如果数据库位于远程服务器上,由于网络延迟,这也是一个真正的问题。
我们多年来一直在使用CachedRowSet
,并且发现了这一点。我们现在实现了我们自己的CachedRowSet
,因为我们从来没有使用任何它的花哨的东西。
我们为所有类型做getString
并转换自己,因为这似乎是最快捷的方式。
这显然不是提取大小的问题,因为postgres驱动程序默认提取所有内容。
答案 2 :(得分:3)
是什么让您认为ResultSet
每次调用rs.next()
时都会检索数据?这取决于它的实现方式 - 如果它一次取出一块,我也不会感到惊讶;很可能是一个相当大的块。
我怀疑你基本上看到将所有数据复制到CachedRowSet
和然后访问它所需的时间 - 基本上你有一个额外的复制操作为no目的
答案 3 :(得分:0)
使用普通ResultSet,您可以使用RowPrefetch和FetchSize获得更多优化选项。
那些优化了网络传输块和while循环中的处理,因此rs.next()总是有一个数据可以使用。
FetchSize的默认设置为10(Oracle最新版本),但据我所知,RowPrefetch未设置。因此意味着网络传输根本没有优化。