线程之间互相不影响;守护线程生活周期相同

引言

这题是一个网友@大脸猫爱吃鱼给我的提问,出自今年校招美团三面的一个真题。大致如下

一个进程有3个线程,如果一个线程抛出oom,其他两个线程还能运行么?

先说一下答案,答案是还能运行

不瞒大家说,真在面试中,我遇到这一题,我估计也是答错。因为我初看到这一题,内心嘿嘿一笑,觉得这题是在考察JVM的内存结构。我第一反应是OOM的常见情况堆溢出,也就是下面的这种异常

java.lang.OutOfMemoryError: Java heap space

先回忆一下,多线程中栈与堆是公有的还是私有的?回答如下

在多线程环境下,每个线程拥有一个栈和一个程序计数器。栈和程序计数器用来保存线程的执行历史和线程的执行状态,是线程私有的资源。其他的资源(比如堆、地址空间、全局变量)是由同一个进程内的多个线程共享。

也就是说,堆是线程共享。那么一个线程堆抛出OOM异常,我第一反应是另外两个线程也抛出OOM异常,毕竟堆是共有的,大家应该都抛出异常。于是,我机智的让@大脸猫爱吃鱼写个代码去测试一下,结果我被啪啪啪打脸了。
测试代码伪如下
一个线程去构造堆溢出,每隔1秒申请一次堆,代码长下面这样

new Thread(() -> {
List<byte[]> list=new ArrayList<byte[]>();
while(true){
System.out.println(new Date().toString()+Thread.currentThread()+"==");
byte[] b = new byte[1024*1024*1];
list.add(b);
try {
Thread.sleep(1000);
} catch (Exception e) {
e.printStackTrace();
}
}
}).start();

另一个线程,睡眠1秒然后输出就好,代码长下面这样

new Thread(() -> {
while(true){
System.out.println(new Date().toString()+Thread.currentThread()+"==");
try {
Thread.sleep(1000);
} catch (Exception e) {
e.printStackTrace();
}
}
}).start();

结果,输出是长下面这样的

大家发现了么,一个线程溢出了,其他线程还在跑,这好像和我们的认知不大一样。坦白说,我看到这个结果,瞬间觉得自己一世英名毁于一旦,从此无法抬起头来做人。没办法了,只能亮出工具来看一下了。
先说一下,在本例测试中,参数如下

-Xms16m -Xmx32m
-Xms 初始堆内存
-Xmx 最大堆内存

接下来,亮出JvisualVM看堆的变化,注意看上面那张图,抛出OOM的时间约在00:11:45左右,因此我们需要重点关注00:11:45左右的曲线变化,如下图所示

如图所示,我们仔细观察一下在00:11:44~00:11:45之间曲线变化,你会发现使用堆的数量,突然间急剧下滑!这代表着一点,当一个线程抛出OOM异常后,它所占据的内存资源会全部被释放掉,从而不会影响其他线程的运行!

讲到这里大家应该懂了,此题的答案为一个线程溢出后,进程里的其他线程还能照常运行。注意了,这个例子我只演示了堆溢出的情况。如果是栈溢出,结论也是一样的,大家可自行通过代码测试。

说时迟,那时快。一个机智的网友又给我提了一个问题?

如果主线程抛异常退出了,子线程还能运行么?

ok,这个问题要从子线程和主线程的关系讲起。
先来一个定义

线程不像进程,一个进程中的线程之间是没有父子之分的,都是平级关系。即线程都是一样的, 退出了一个不会影响另外一个。

因此,答案是如果主线程抛异常退出了,子线程还能运行。
但是有一个例外情况,如果这些子线程都是守护线程,那么子线程会随着主线程结束而结束。

作者:孤独烟
出处:http://rjzheng.cnblogs.com/

本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。如果觉得还有帮助的话,可以点一下右下角的【推荐】

一个线程oom,进程里其他线程还能运行吗?的更多相关文章

  1. 【原创】一个线程oom,进程里其他线程还能运行吗?

    引言 这题是一个网友@大脸猫爱吃鱼给我的提问,出自今年校招美团三面的一个真题.大致如下 一个进程有3个线程,如果一个线程抛出oom,其他两个线程还能运行么? 先说一下答案,答案是还能运行 不瞒大家说, ...

  2. 进击的Python【第九章】:paramiko模块、线程与进程、各种线程锁、queue队列、生产者消费者模型

    一.paramiko模块 他是什么东西? paramiko模块是用python语言写的一个模块,遵循SSH2协议,支持以加密和认证的方式,进行远程服务器的连接. 先来个实例: import param ...

  3. Python 开启线程的2中方式,线程VS进程(守护线程、互斥锁)

    知识点一: 进程:资源单位 线程:才是CPU的执行单位 进程的运行: 开一个进程就意味着开一个内存空间,存数据用,产生的数据往里面丢 线程的运行: 代码的运行过程就相当于运行了一个线程 辅助理解:一座 ...

  4. 12 并发编程-(线程)-线程queue&进程池与线程池

    queue 英 /kjuː/ 美 /kju/ 队列 1.class queue.Queue(maxsize=0) #队列:先进先出 import queue q=queue.Queue() q.put ...

  5. day35:线程队列&进程池和线程池&回调函数&协程

    目录 1.线程队列 2.进程池和线程池 3.回调函数 4.协程:线程的具体实现 5.利用协程爬取数据 线程队列 1.线程队列的基本方法 put 存 get 取 put_nowait 存,超出了队列长度 ...

  6. GIL全局解释器锁+GIL全局解释器锁vs互斥锁+定时器+线程queue+进程池与线程池(同步与异步)

    以多线程为例写个互斥锁 from threading import Thread ,Lockimport timemutex = Lock() n = 100 def task(): global n ...

  7. 计算机必知必会:进程process与线程thread 进程定义为一个正在运行的程序的实例

    http://www.nowamagic.net/librarys/veda/detail/1741进程和线程这对概念的理解也是很难的,至今网络上可查的资料对其的理解出入都挺大,在不同的操作系统中,如 ...

  8. paramiko模块,线程,进程

    关于paramiko模块 paramiko是基于Python实现的ssh2远程安全连接,支持认证及密钥方式远程执行命令.文件传输,中间ssh代理等 paramiko的安装: 安装好之后,用parami ...

  9. Linux 线程与进程,以及通信

    http://blog.chinaunix.net/uid-25324849-id-3110075.html 部分转自:http://blog.chinaunix.net/uid-20620288-i ...

随机推荐

  1. javascript模块化之CommonJS、AMD、CMD、UMD、ES6

    javascript模块化之CommonJS.AMD.CMD.UMD.ES6 一.总结 一句话总结: CommonJS是同步加载模块,用在服务端:AMD是异步加载模块,用于浏览器端 1.为什么服务器端 ...

  2. Android 客户端应用开发结构框架

    本文算是一篇漫谈,谈一谈关于android开发中工程初始化的时候如何在初期我们就能搭建一个好的架构.关于android架构,因为手机的限制,目前我觉得也确实没什么大谈特谈的,但是从开发的角度,看到整齐 ...

  3. BOSCH汽车工程手册————混合驱动

    首先放一波资源,一千两百多页的pdf 链接:https://pan.baidu.com/s/15IsvHqOFCnqAKwY_SR4-lA提取码:6wmz 混合驱动 混合驱动有串联驱动并联驱动以及两种 ...

  4. Linux-Ubuntu目录

    ubuntu没有盘符这个概念,只有一个根目录/,所有文件都在它下面 /:根目录,一般根目录下只存放目录,在Linux下有且只有一个根目录.所有的东西都是从这里开始.当你在终端里输入“/home”,你其 ...

  5. docker(常见调试技巧):docker打包镜像调试技巧

    写Dockerfile可以先不指定CMD.ENTRYPOINT等启动命令,只要拷贝就好了 如下: # Dockerfile for basic-app-client # Build with: # d ...

  6. Haproxy 代理

    一:安装haproxy 1:解压   编译   安装 tar zxf haproxy-1.7.9.tar.gz cd  haproxy-1.7.9 uname -e make TARGET=linux ...

  7. 禁止在DBGrid中按delete删除记录

    procedure TForm1.DBGrid1KeyDown(Sender: TObject; var Key: Word; Shift: TShiftState);begin  if (ssctr ...

  8. 精通CSS:高级Web标准解决方案(第二版) 初读笔记

    2.1 常用的选择器 1. 类型选择器  p { color: black; } 2. 后代选择器  blockquote p { padding-left: 2em; } 3. ID选择器  #in ...

  9. Python学习之表的数据类型

    数据类型 数值类型 类型 大小 范围(有符号) 范围(无符号)unsigned约束 用途 TINYINT 1 字节 (-128,127) (0,255) 小整数值 SMALLINT 2 字节 (-32 ...

  10. KVM虚拟机管理(2)

    一.virt-manager创建虚机 命令行需要下载下面的组件: CentOS7: 命令行界面升级为图形化界面 yum groupinstall "X Window System" ...