您的位置:首页 > 其它

JVM中算法和OOM

2020-03-28 20:16 134 查看

一、GC垃圾回收

GC四大算法
1.引用计数
2.复制算法
3.标记清除
4.标记整理压缩
现在一般使用可达性算法GCroot.
新生代用复制算法其中谁空谁是to,操作过程是:先把from中的对象复制到to中,然后from区和to区交换,再清空to,所以谁空谁是to.每当幸存一次,就会导致这个对象的年龄+1;如果这个年龄值大于15就会进入养老区!;
老年代用标记整理压缩算法,所以目前GC垃圾回收是用了分代收集算法,没有最好的,只有最合适的。

二、OOM

java.lang.StackOverflowError

public static void main(String[] args) {
a();
}

public static void a(){
a();
}

java.lang.OutOfMemoryError: Java heap space

// -Xms10m -Xmx10m
public class OomDemo {
public static void main(String[] args) {
String str = "Coding";
while (true){
str += str + new Random(1111111111) +  new Random(1111111111);
}
}
}

java.lang.OutOfMemoryError: GC overhead limit exceeded

GC 回收时间过长也会导致 OOM;

可能CPU占用率一直是100%,GC 但是没有什么效果!

// -Xms10m -Xmx10m -XX:MaxDirectMemorySize=5m -XX:+PrintGCDetails
public class OomDemo {
public static void main(String[] args) throws Throwable {
int i = 0;
List<String> list = new ArrayList<String>();

try {
while (true){
list.add(String.valueOf(++i).intern());
}
} catch (Throwable e) {
System.out.println("i=>"+i);
e.printStackTrace();
throw e;
}
}
}
java.lang.OutOfMemoryError: Direct buffer memory 基础缓冲区的错误!
// -Xms10m -Xmx10m -XX:MaxDirectMemorySize=5m -XX:+PrintGCDetails
public class OomDemo {
public static void main(String[] args) throws Throwable {
System.out.println("配置的MaxDirectMemorySize"
+VM.maxDirectMemory()/(double)1024/1024+"MB");

TimeUnit.SECONDS.sleep(2);

// 故意破坏!
// ByteBuffer.allocate(); 分配JVM的堆内存,属于GC管辖
// ByteBuffer.allocateDirect() ; // 分配本地OS内存,不属于GC管辖
ByteBuffer byteBuffer = ByteBuffer.allocateDirect(6 * 1024 * 1024);
// java.lang.OutOfMemoryError: Direct buffer memory
}
}

java.lang.OutOfMemoryError: unable to create native Thread

高并发 , unable to create native Thread这个错误更多的时候和平台有关!

1、应用创建的线程太多!

2、服务器不允许你创建这么多线程!

public class TDemo {
public static void main(String[] args) {
for (int i = 1; ; i++) {
System.out.println("i=>"+i);
new Thread(()->{
try {
Thread.sleep(Integer.MAX_VALUE);
} catch (InterruptedException e) {
e.printStackTrace();
}
},""+i).start();
}
}
}

Exception in thread “main” java.lang.OutOfMemoryError: unable to create new native thread

1、服务器线程不够了,超过了限制,也会爆出OOM异常!

java.lang.OutOfMemoryError: Metaspace 元空间报错

java8 之后使用元空间代替永久代;本地内存!

1、虚拟机加载类信息

2、常量池

3、静态变量

4、编译后的代码

模拟元空间溢出、不断的生成类即可!

// -XX:MetaspaceSize=10m -XX:MaxMetaspaceSize=10m
public class OomDemo {

static class OOMTest{}

public static void main(String[] args) throws Throwable {

int i = 0; // 模拟计数器

try {
while (true){
i++;
// 不断的加载对象! Spring的 cglib;
Enhancer enhancer = new Enhancer();
enhancer.setSuperclass(OOMTest.class);
enhancer.setUseCache(false);
enhancer.setCallback(new MethodInterceptor() {
@Override
public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
return method.invoke(o,args);
}
});
enhancer.create();
}
} catch (Throwable e) {
System.out.println("i=>"+i);
e.printStackTrace();
}

}
}
  • 点赞
  • 收藏
  • 分享
  • 文章举报
qq_28945483 发布了6 篇原创文章 · 获赞 0 · 访问量 65 私信 关注
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: