- PR -

SQLの結果セット取得とOutOfMemoryError

1
投稿者投稿内容
未記入
ベテラン
会議室デビュー日: 2005/04/16
投稿数: 51
投稿日時: 2005-08-18 08:24
いつもお世話になっております。

次のような環境でJavaプログラムを実行しています。
(バッチジョブです。)
java.lang.OutOfMemoryErrorが発生して困っています。

OS:Mac OS X Server バージョン10.4
プロセッサ:1.8GHz PowerPC G5
メモリ:1GB
DBMS : PostgresSQL 8.0.1
JDBCドライバ:Postgresql-8.0-311.jdbc3
※ プログラムはEclipse3.0上から直接実行。

以前同じ環境で正常終了していたプログラムを
久しぶりに実行しました。
するとそのプログラムには何も修正が入っていませんでしたが
java.lang.OutOfMemoryErrorが発生してしまいました。

このプログラムは冒頭で次のようなSQLを発行し
結果セットを取得して処理を行います。

SELECT * FROM Public.TEST1 a,
(SELECT AA, BB, CC, DD, MAX(EE) as E
FROM Public.TEST2
GROUP BY AA, BB, CC, DD) b
WHERE a.AA = b.AA and
a.BB = b.BB and
a.CC = b.CC and
a.DD = b.DD and
b.E = '0'
ORDER BY a.AA, a.BB, a.CC, a.DD, a.FF

ここで、TEST1テーブルのレコード件数は118万9637件、
TEST2テーブルのレコード件数は1万1785件です。

Terminal上からDBMSに対して直接このSQLを発行すると
15分程度経過後に結果が表示されます。

Java上からこのSQLを発行した後
20〜30分程度は動いていますが
結局 結果セットを取得する最中にOutOfMemoryErrorが
発生しています。
(結果セット取得後に続くwhile(ResultSet.next())まで到達しません。)

vm_statを参照するとFreeの仮想メモリは当該処理開始後に
20M程度から1M未満(900K程度)まで一気に減りますが、
かといってその後はその値がそれほど変化しません。

また処理中のPostgresのCPU使用率はそれほど高くはありません。
(30%台)

対処として、
@ DBMSのvacuumdbコマンドを利用し
不要なデータ領域を解放させました。
(現在は当DBに大量のデータが入っているので3時間程度要しました。)
A Javaコマンドの引数でJVM用のメモリを1024Mまで取れるように設定していましたが
あえてこれを512Mにまで減らしました。
(他のプロセスがより多くのメモリを使えるようにするため。)
(物理メモリ一杯にJava用メモリを確保するのは
逆に良くないという情報も得たため。)
B 以前実行したときと大きく異なるのは、
何よりも
他のテーブルにもデータが大量に入っていることです。
そのため、とりあえずAテーブル(2万4千件)、
Bテーブル(2万4千件)、
Cテーブル(2万4千件)、
Dテーブル(1万585件)、
Eテーブル(125件)、
Fテーブル(75件)
を全件Deleteしました。
(これらは当該処理後シーケンシャルに実行されるジョブの結果を
格納するテーブルです。)


しかし、いずれの対処を行ってもOutOfMemoryエラーになることは同じでした。

他に何か必要な対応方法、アドバイス等を
何卒宜しくお願い申し上げます。

かつのり
ぬし
会議室デビュー日: 2004/03/18
投稿数: 2015
お住まい・勤務地: 札幌
投稿日時: 2005-08-18 21:59
レコードを全てJavaの方へ引っ張ってきていませんか?
ConnectionからStatementオブジェクトを取得する時に、
ResultSetクラスの定数をオプションとして使用することによって
改善しませんかね。
1

スキルアップ/キャリアアップ(JOB@IT)