我在一个程序中得到这个错误,该程序创建了几个(几十万个)HashMap对象,每个对象有几个(15-20)个文本条目.在提交到数据库之前,必须收集这些字符串(不会分解成较小的数量).
根据Sun的说法,如果在垃圾收集中花费了太多时间,则会发生错误:如果超过98%的总时间花在垃圾收集上,并且不到2%的堆被恢复,则会抛出OutOfMemoryError. ".
显然,可以使用命令行将参数传递给JVM
第一种方法工作正常,第二种方法在另一个java.lang.OutOfMemoryError中结束,这次是关于堆的.
所以,问题:对于特定的用例(即几个小的HashMap对象),是否有任何编程替代方案?例如,如果我使用HashMap clear()方法,问题就会消失,但HashMap中存储的数据也会消失!:-)
StackOverflow中的相关主题也讨论了该问题.
由于Java 7将默认使用新的G1垃圾收集,Java是否能够处理一个数量级更大的堆而不会产生"破坏性"的GC暂停时间?有人在生产中实际实施了G1,你的经历是什么?
公平地说,我唯一一次看到非常长的GC暂停是非常大的堆,远远超过工作站.澄清我的问题; G1将打开数百GB的网关?TB?
Java 7已经出现了一段时间了,但我找不到任何关于垃圾收集器配置的好资源,特别是新的G1收集器.
我的问题:
String s = "";
for(i=0;i<....){
s = some Assignment;
}
Run Code Online (Sandbox Code Playgroud)
要么
for(i=0;i<..){
String s = some Assignment;
}
Run Code Online (Sandbox Code Playgroud)
我不需要再次在循环外使用's'了.第一个选项可能更好,因为每次都不会初始化新的String.然而,第二个将导致变量的范围限于循环本身.
编辑:回应Milhous的回答.将String分配给循环中的常量是没有意义的吗?不,这里'一些分配'意味着从迭代的列表中获得的变化值.
此外,问题不是因为我担心内存管理.只是想知道哪个更好.
这是我第一次使用Proguard时,我注意到如果你添加许多自定义规则,proguard-project.txt那么显然需要更多的时间来构建.这导致Eclipse崩溃报告GC overhead limit exceeded,然后我必须强制关闭java,因为编辑器继续弹出错误和警告对话框.有没有办法避免Eclipse上的这些连续崩溃,所以解决这里报告的问题呢?
我的方法是创建十万个本地集合并用随机字符串填充它们,如下所示:
SecureRandom random = new SecureRandom();
for(int i = 0 ; i < 100000 ; i++){
HashMap<String, String> map = new HashMap<String, String>();
for(int j = 0 ; j < 30 ; j++){
map.put(new BigInteger(130, random).toString(32), new BigInteger(130, random).toString(32));
}
}
Run Code Online (Sandbox Code Playgroud)
我也提供了-XX:+ UseGCOverheadLimit jvm参数,但无法获取错误.是否有任何简单可靠的方法/黑客来获取此错误?
我正在使用GWT和GAE开发应用程序.当我尝试重建它或创建一个工件时,我会在下面的图片中看到很多错误.
我搜索了谷歌和Stack Overflow,我得到了一些答案,但不是我的特殊问题.
根据我的理解,我得到了错误,因为我的垃圾收集器消耗了大量内存.

这是主要的错误Exception in thread "main" java.lang.OutOfMemoryError: GC overhead limit exceeded.
在java中,你是否有可能得到一个OutOfMemoryError异常,即使应该有足够的内存应该垃圾收集释放更多的内存?换句话说,如果没有足够的内存来分配,在抛出OutOfMemoryError之前是否会强制gc运行?
谢谢.
我有一小段代码,每五分钟就会截取一次我的桌面截图 - 这是一个轻松思考的工作,并计算出多少截图,比如facebook ...
然而,我对它占用的内存量感到有点困惑 - 通常它会爬升到200mb的RAM,我确信这是多余的......任何人都可以告诉我一个减少内存占用的合理方法或b)它为什么涨可言?
/**
* Code modified from code given in http://whileonefork.blogspot.co.uk/2011/02/java-multi-monitor-screenshots.html following a SE question at
* http://stackoverflow.com/questions/10042086/screen-capture-in-java-not-capturing-whole-screen and then modified by a code review at http://codereview.stackexchange.com/questions/10783/java-screengrab
*/
package com.tmc.personal;
import java.awt.AWTException;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.Rectangle;
import java.awt.Robot;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.TimeZone;
import java.util.concurrent.TimeUnit;
import javax.imageio.ImageIO;
class ScreenCapture {
static int minsBetweenScreenshots = 5;
public static void main(String args[]) {
int …Run Code Online (Sandbox Code Playgroud) 偶尔,在每两天一次到每两周一次之间,我的应用程序在代码中看似随机的位置崩溃:java.lang.OutOfMemoryError: GC overhead limit exceeded.如果我谷歌这个错误,我来到这个问题,并引导我到这个阳光文件,它表示:
如果在垃圾收集中花费了太多时间,并行收集器将抛出OutOfMemoryError:如果在垃圾收集中花费了超过98%的总时间并且恢复了少于2%的堆,则将抛出OutOfMemoryError.此功能旨在防止应用程序长时间运行,同时由于堆太小而很少或没有进度.如有必要,可以通过在命令行中添加选项-XX:-UseGCOverheadLimit来禁用此功能.
这告诉我,我的应用程序显然占用了垃圾收集总时间的98%,只能恢复2%的堆.
但98%的时间是什么时候?应用程序运行的整个两周的98%?最后一毫秒的98%?
我正在尝试确定一个实际解决这个问题的最佳方法,而不仅仅是使用,-XX:-UseGCOverheadLimit但我觉得需要更好地理解我正在解决的问题.