2010-08-09 81 views
4

我收到此錯誤:Java堆內存錯誤

Exception in thread "main" java.lang.OutOfMemoryError: Java heap space 
    at com.mysql.jdbc.MysqlIO.nextRowFast(MysqlIO.java:1585) 
    at com.mysql.jdbc.MysqlIO.nextRow(MysqlIO.java:1409) 
    at com.mysql.jdbc.MysqlIO.readSingleRowSet(MysqlIO.java:2886) 
    at com.mysql.jdbc.MysqlIO.getResultSet(MysqlIO.java:476) 
    at com.mysql.jdbc.MysqlIO.readResultsForQueryOrUpdate(MysqlIO.java:2581) 
    at com.mysql.jdbc.MysqlIO.readAllResults(MysqlIO.java:1757) 
    at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2171) 
    at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2562) 
    at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2512) 
    at com.mysql.jdbc.StatementImpl.executeQuery(StatementImpl.java:1476) 
    at DBase.connect(automateExport.java:31) 
    at automateExport.main(automateExport.java:10) 

我試圖打開eclipse.ini文件,然後改變

-Xms 256m and -Xmx 512m 

增加堆內存空間的但是這並沒有幫助。我試過512m和1024m,但最終出現錯誤:無法啓動JVM和eclipse沒有打開。

我試圖做同樣的CMD線:

java -Xms 256m and -Xmx 512m 

也蝕-vmargs -Xms 256m and -Xmx 512m 但仍然沒有幫助。 我基本上是創建一個JDBC連接來查詢數據庫非常大的記錄集。 請幫幫我。

+0

有多少條記錄? – 2010-08-09 20:36:38

+0

這是什麼類型的應用程序,您可以更詳細地瞭解一旦獲得該數據後您想要處理的所有數據?你想展示給用戶嗎?做計算? – 2010-08-09 21:05:44

回答

8

當你查詢返回非常大大集,MySQL驅動程序默認情況下會加載整個結果集在內存之前,讓你控制回來。這聽起來像是你的內存不足了,所以增加內存,例如-Xmx1024M

另一種選擇可能是在MySQL查詢上啓用流結果 - 這可以防止整個ResultSet一次加載到內存中。這可以通過執行

stmt = conn.createStatement(java.sql.ResultSet.TYPE_FORWARD_ONLY, 
      java.sql.ResultSet.CONCUR_READ_ONLY);//These are defaults though,I believe 
stmt.setFetchSize(Integer.MIN_VALUE); 

來完成(需要注意的是任何東西,但Integer.MIN_VALUE的對MySQL驅動程序沒有影響)

+0

謝謝你們所有的信息。 stmt = conn.createStatement(java.sql.ResultSet.TYPE_FORWARD_ONLY, java.sql.ResultSet.CONCUR_READ_ONLY); //這些是默認值,但我相信 stmt.setFetchSize(Integer.MIN_VALUE); 這工作!所以鬆了一口氣! :) – JJunior 2010-08-09 21:37:38

+0

不幸的是,這個解決方案爲Spring(2 mio記錄)帶來了「流操作結果集不支持的操作」異常。幸運的是,增加Xms確實有幫助。 – 2012-03-05 11:57:54

0

嘗試將您的數據拆分爲多個結果集。考慮一下從數據庫中取回數據後,你想要做什麼。結果集太大而不適合堆空間。

0

查詢的全部結果是否必須在內存中?如果是,那麼你應該購買更多的內存。如果不是的話,那麼劃分問題將是適當的解決方案。在很多情況下,您甚至可以讓數據庫爲您整合數據。

如果您對給定問題的解決方案不能很好地滿足數據量的要求,那麼即使通過擴展RAM也會返回到此問題。所以真正好的解決方案是根本避免這種情況。

0

Lazy Load是否適用?你可以使用上限來限制分段查詢的結果嗎?

1

您不必擔心-Xms太多 - 這是啓動時的初始堆大小。

-Xmx是最大Heap大小。嘗試增加它,直到您不再獲取OutOfMemory異常,或者直到內存不足。

如果內存不足,則無法一次加載整個ResultSet,而需要應用其他人提到的方法。

0

我發現,MySQL驅動程序出現內存泄漏。我在連接池設置中將它與tomcat一起使用。 JDBCResultSet和StatementImpl對象的負載位於堆中。在tomcat中設置數據源配置(context.xml)中的maxAge幫助。