2

メモリリークに問題があります。私のコードのこのスキーマ:

CallableStatement c = Baza.conn.prepareCall("select * from something");           
ResultSet rs = c.executeQuery();//takes about 100sec

while(rs.next())
{
//do stuff, only calculations, I don't create any object
}   

rs.close();
c.close();

実行中executeQueryの RAM の使用量は 300MB まで上昇し、二度と低下することはありません。プログラムが再び同じ場所にある場合 (ただし、選択がわずかに異なる場合)、RAM の使用量が再び増加する場合とそうでない場合があります。私はただ閉じるだけではありResultSetませんか?数時間ごとにそのプログラムを再起動する必要があるため、助けていただければ幸いです。

JDBC4 と posgresql を使用しています

4

4 に答える 4

1

カーソルを使用してフェッチサイズを設定すると、クエリのメモリ使用量を減らすことができます。

Baza.conn.setAutoCommit(false); // Turn off autocommit on the connection to enable cursors in JDBC
CallableStatement c = Baza.conn.prepareCall("select * from something");           
c.setFetchSize(1000); // The fetch size determines the number of records returned in each "Batch"
ResultSet rs = c.executeQuery();// This may appear to run faster depending on the query

// Nothing changes here.  The JDBC driver handles the cursor for you.
while(rs.next())
{
//do stuff, only calculations, I don't create any object
}   

rs.close(); // This will close the cursor
c.close(); // I would recommend re-enabling autocommit if you weren't closing the connection here
于 2013-02-15T18:32:48.420 に答える
0

クエリに時間がかかる場合は、接続が非常に遅いか、大量のデータが返される可能性があります。すべてのデータを RAM に保持することは、最善の解決策ではありません。Jigar Joshi のコメントがすでに指摘しているように、ページングを調べたいと思うかもしれません。また、接続も閉じることをお勧めします。ガベージ コレクションについては、Java7 を検討してください。新しいガベージ コレクタがあります (たとえば、Java 7 (JDK 7) ガベージ コレクションと G1 に関するドキュメントを参照)。

于 2013-02-15T18:20:09.717 に答える
0

「conn」も必ず閉じてください。

JVM はメモリを内部的に管理します。OS から報告された RAM 使用率がすぐに解放されるとは限りません。最終的には、JVM がガベージ コレクションを実行するときに解放する必要があります。JMX リスナーを構成し、JConsole を使用して JVM メモリを監視し、OS を信頼しません。

于 2013-02-15T18:13:59.100 に答える