工作中碰到过这个问题好几次了,觉得有必要总结一下,所以有了这篇文章,这篇文章分为三个部分:认识问题、分析问题、解决问题。

一、认识问题:

首先我们通过下面这个 测试程序 来认识这个问题:

运行的环境 (有必要说明一下,不同环境会有不同的结果):32位 Windows XP,Sun JDK 1.6.0_18, eclipse 3.4,

测试程序:

  1. import java.util.concurrent.CountDownLatch;
  2. public class TestNativeOutOfMemoryError {
  3. public static void main(String[] args) {
  4. ;; i++) {
  5. System.out.println("i = " + i);
  6. new Thread(new HoldThread()).start();
  7. }
  8. }
  9. }
  10. class HoldThread extends Thread {
  11. );
  12. public HoldThread() {
  13. this.setDaemon(true);
  14. }
  15. public void run() {
  16. try {
  17. cdl.await();
  18. } catch (InterruptedException e) {
  19. }
  20. }
  21. }

不指定任何JVM参数,eclipse中直接运行输出,看到了这位朋友了吧:

i = 5602 

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

    at java.lang.Thread.start0(Native Method)

    at java.lang.Thread.start(Thread.java:597)

    at TestNativeOutOfMemoryError.main(TestNativeOutOfMemoryError.java:20)

二、分析问题:

这个异常问题本质原因是我们创建了太多的线程,而能创建的线程数是有限制的,导致了异常的发生。能创建的线程数的具体计算公式如下: 

(MaxProcessMemory - JVMMemory - ReservedOsMemory) / (ThreadStackSize) = Number of threads

MaxProcessMemory 指的是一个进程的最大内存

JVMMemory         JVM内存

ReservedOsMemory  保留的操作系统内存

ThreadStackSize      线程栈的大小



在java语言里, 当你创建一个线程的时候,虚拟机会在JVM内存创建一个Thread对象同时创建一个操作系统线程,而这个系统线程的内存用的不是JVMMemory,而是系统中剩下的内存(MaxProcessMemory - JVMMemory - ReservedOsMemory)。 





结合上面例子我们来对公式说明一下: 

MaxProcessMemory 在32位的 windows下是 2G

JVMMemory   eclipse默认启动的程序内存是64M

ReservedOsMemory  一般是130M左右

ThreadStackSize 32位 JDK 1.6默认的stacksize 325K左右

公式如下:

(2*1024*1024-64*1024-130*1024)/325 = 5841 

公式计算所得5841,和实践5602基本一致(有偏差是因为ReservedOsMemory不能很精确) 



由公式得出结论:你给JVM内存越多,那么你能创建的线程越少,越容易发生java.lang.OutOfMemoryError: unable to create new native thread。 



咦,有点背我们的常理,恩,让我们来验证一下,依旧使用上面的测试程序,加上下面的JVM参数,测试结果如下: 

ThreadStackSize      JVMMemory                    能创建的线程数

默认的325K             -Xms1024m -Xmx1024m    i = 2655

默认的325K               -Xms1224m -Xmx1224m    i = 2072

默认的325K             -Xms1324m -Xmx1324m    i = 1753

默认的325K             -Xms1424m -Xmx1424m    i = 1435

-Xss1024k             -Xms1424m -Xmx1424m    i = 452 

完全和公式一致。 



三、解决问题: 

1, 如果程序中有bug,导致创建大量不需要的线程或者线程没有及时回收,那么必须解决这个bug,修改参数是不能解决问题的。

2, 如果程序确实需要大量的线程,现有的设置不能达到要求,那么可以通过修改MaxProcessMemory,JVMMemory,ThreadStackSize这三个因素,来增加能创建的线程数:

a, MaxProcessMemory 使用64位操作系统

b, JVMMemory   减少JVMMemory的分配

c, ThreadStackSize  减小单个线程的栈大小

解决 - java.lang.OutOfMemoryError: unable to create new native thread的更多相关文章

  1. 解决java.lang.OutOfMemoryError: unable to create new native thread问题

    解决:1.升级JVM到最新的版本 最新版本的JVM一般在内存优化方面做的更好,升级JVM到最新的版本可能会缓解测问题2.从操作系统层面去解决 使用64位操作系统 如果使用32位操作系统遇到unable ...

  2. java.lang.OutOfMemoryError: unable to create new native thread如何解决

    工作中碰到过这个问题好几次了,觉得有必要总结一下,所以有了这篇文章,这篇文章分为三个部分:认识问题.分析问题.解决问题. 一.认识问题: 首先我们通过下面这个 测试程序 来认识这个问题:运行的环境 ( ...

  3. 记一次内存溢出java.lang.OutOfMemoryError: unable to create new native thread

    一.问题: 春节将至,系统访问量进入高峰期.随之系统出现了异常:java.lang.OutOfMemoryError: unable to create new native thread.在解决这个 ...

  4. [java] [error] java.lang.OutOfMemoryError: unable to create new native thread

    前言 最近公司的服务器出现了oom的报错,经过一番排查,终于找到了原因.写下这篇博客是为了记录下查找的过程,也是为了帮助那些跟我门遇到的情况相同的人可以更快的寻找到答案. 环境 系统:linux(ce ...

  5. JVM内存越多,能创建的线程越少,越容易发生java.lang.OutOfMemoryError: unable to create new native thread。

    一.认识问题: 首先我们通过下面这个 测试程序 来认识这个问题:运行的环境 (有必要说明一下,不同环境会有不同的结果):32位 Windows XP,Sun JDK 1.6.0_18, eclipse ...

  6. spark java.lang.OutOfMemoryError: unable to create new native thread

    最近迁移集群,在hadoop-2.8.4 的yarn上跑 spark 程序 报了以下错误 java.lang.OutOfMemoryError: unable to create new native ...

  7. 剥下“java.lang.OutOfMemoryError: unable to create new native thread”的外衣 创建线程数公式(MaxProcessMemory - JVMMemory – ReservedOsMemory)

    剥下“java.lang.OutOfMemoryError: unable to create new native thread”的外衣 星期一早上到了公司,据称产品环境抛出了最可爱的异常—OutO ...

  8. 关于“java.lang.OutOfMemoryError : unable to create new native Thread”的报错问题

    好吧 我发誓这是postgresql的Mirroring Controller的RT测试的最后一个坑了. 在这个RT测试的最后,要求测试Mirroring Controller功能在长时间运行下的稳定 ...

  9. spark大批量读取Hbase时出现java.lang.OutOfMemoryError: unable to create new native thread

    这个问题我去网上搜索了一下,发现了很多的解决方案都是增加的nproc数量,即用户最大线程数的数量,但我修改了并没有解决问题,最终是通过修改hadoop集群的最大线程数解决问题的. 并且网络上的回答多数 ...

  10. 再谈 Unlix (Linux, AIX, HPUX) 上 Java 的 java.lang.OutOfMemoryError: unable to create new native thread

    首先很容易排除是 程序问题 内存用了很少,64 位 Java也没有内存限制,线程也不多,-Xss 堆栈也没人会配置很大. 那么肯定是 limit 不足引起 配置 ulimit 就可以了,问题看起来很简 ...

随机推荐

  1. Android studio导入第三方类库

    1.开发过程中想要导入第三方类库和Eclipse也是有差别的,我们导入SlidingMenu这个类库,从github上下载下来解压到项目目录下. 2.然后我们重启我们的android studio就会 ...

  2. 定位vc运行时库问题 依赖问题,屡试不爽的一招

    用vc 菜单 文件| 打开|指定EXE或DLL,如有指定运行时库,则PE文件的资源中可以看到manifest 配置节 然后据此判断EXE依赖的运行时库, 再根据编译选项调整 运行时库设置

  3. Java泛型之<T>

    这里不讲泛型的概念和基础知识,就单纯的就我的理解说一下泛型中的<T> 一. <T> 下面的一段码就可以简单使用了<T>参数,注释就是对<T>的解释. p ...

  4. Java程序员们最常犯的10个错误(转)

    1.将数组转化为列表 将数组转化为一个列表时,程序员们经常这样做: 1 List<String> list = Arrays.asList(arr); Arrays.asList(&quo ...

  5. Everything You Wanted to Know About Machine Learning

    Everything You Wanted to Know About Machine Learning 翻译了理解机器学习的10个重要的观点,增加了自己的理解.这些原则在大部分情况下或许是这样,可是 ...

  6. MFC模态对话框的消息循环

    MFC模态对话框的消息循环 单线程程序, 当主窗口响应函数中弹出模态对话框时,为什么主窗口响应函数可能照常工作? 当弹出模态对话框时,线程的消息循环无法返回,父窗口的事件本应没人处理,应该处于卡死状态 ...

  7. Django写的投票系统4(转)

    原文地址:http://www.cnblogs.com/djangochina/archive/2013/06/04/3114269.html 现在已经可以在后台管理投票了,现在就差怎么在前台显示和如 ...

  8. poj1155(树形dp)

    题目链接:http://poj.org/problem?id=1155 题意:电视台要直播一场比赛,电视网络刚好形成了一棵树,其中有M个为客户端,其他的为中转站,其中中转站与中转站以及中转站与客户端之 ...

  9. Bootstrap之表格

    基本实例 为随意<table>标签加入.table类能够为其赋予主要的样式-少量的内补(padding)和水平方向的分隔线. <table class="table&quo ...

  10. sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)

    在使用Hibernate的J2EE项目中,莫名其妙出现如上错误,既不报错,也不运行不论什么输出測试代码,更不返回结果. 经过排查,在方法里面引用的实体类和其映射文件属性个数不一致. 改动一致后,即解决 ...