前言

今天在开发中对Java程序的退出产生了困惑,因为题主之前写过一段时间Go,这两者的程序退出逻辑是不同的,下面首先给出结论,再通过简单的例子来介绍。

对于Java程序,Main线程退出,如果当前存在非守护线程,则Java程序会等待非守护线程都执行完再退出;如果只存在守护线程,则会直接退出。这是JVM底层实现的机制。

对于Go程序,如果main协程已经退出,那么其他任何协程都将退出。在非main协程中创建的子协程,如果父协程退出了,子协程依然可以正常运行。

Java程序退出

package main.java.io;

import java.io.IOException;

public class Test {
/**
* main线程退出后,如果当前只存在其他的守护线程,则程序会直接退出;
* 如果存在非守护线程,则会等待其他守护线程执行完毕,这是jvm底层实现机制
*/
public static void main(String[] args) throws IOException {
System.out.println("main start");
Thread t1 = new Thread(() -> {
System.out.println("t1 start");
try {
Thread.sleep(2000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("t1 exit");
});
t1.setDaemon(true);
t1.start();
System.out.println("main exit");
}
}

如果没有t1.setDaemon(true),那么主线程退出后,t1线程执行完之后程序才退出;否则,主程序退出后程序直接终止。

Go程序退出

package main

import (
"fmt"
"time"
) func test() {
go func() {
fmt.Println("father start")
go func() {
fmt.Println("son start")
time.Sleep(time.Second)
fmt.Println("son exit")
}()
fmt.Println("father exit")
}()
} func main() {
fmt.Println("main start")
test()
time.Sleep(time.Second * 2)
go func() {
fmt.Println("t1 start")
fmt.Println("t1 exit")
}()
fmt.Println("main exit")
} // 结果:
// main start
// father start
// father exit
// son start
// son exit
// main exit

father协程已经退出,但son协程依然执行了。当main协程退出后,t1协程也直接终止。

参考

浅谈Java和Go的程序退出的更多相关文章

  1. 浅谈Java语言中try{}catch{}和finally{}的执行顺序问题

    浅谈Java语言中try{}catch{}和finally{}的执行顺序问题 2019-04-06  PM  13:41:46  1. 不管有没有出现异常,finally块中代码都会执行: 2. 当t ...

  2. 浅谈Java回收对象的标记和对象的二次标记过程_java - JAVA

    文章来源:嗨学网 敏而好学论坛www.piaodoo.com 欢迎大家相互学习 一.对象的标记 1.什么是标记?怎么标记? 第一个问题相信大家都知道,标记就是对一些已死的对象打上记号,方便垃圾收集器的 ...

  3. 浅谈Java的throw与throws

    转载:http://blog.csdn.net/luoweifu/article/details/10721543 我进行了一些加工,不是本人原创但比原博主要更完善~ 浅谈Java异常 以前虽然知道一 ...

  4. 浅谈Java中的对象和引用

    浅谈Java中的对象和对象引用 在Java中,有一组名词经常一起出现,它们就是“对象和对象引用”,很多朋友在初学Java的时候可能经常会混淆这2个概念,觉得它们是一回事,事实上则不然.今天我们就来一起 ...

  5. 浅谈JAVA集合框架

    浅谈JAVA集合框架 Java提供了数种持有对象的方式,包括语言内置的Array,还有就是utilities中提供的容器类(container classes),又称群集类(collection cl ...

  6. 浅谈java性能分析

    浅谈java性能分析,效能分析 在老师强烈的要求下做了效能分析,对上次写过的词频统计的程序进行分析以及改进. 对于效能分析:我个人很浅显的认为就是程序的运行效率,代码的执行效率等等. java做性能测 ...

  7. !! 浅谈Java学习方法和后期面试技巧

    浅谈Java学习方法和后期面试技巧 昨天查看3303回复33 部落用户大酋长 下面简单列举一下大家学习java的一个系统知识点的一些介绍 一.java基础部分:java基础的时候,有些知识点是非常重要 ...

  8. 【转】浅谈Java中的hashcode方法(这个demo可以多看看)

    浅谈Java中的hashcode方法 哈希表这个数据结构想必大多数人都不陌生,而且在很多地方都会利用到hash表来提高查找效率.在Java的Object类中有一个方法: public native i ...

  9. 浅谈java类集框架和数据结构(2)

    继续上一篇浅谈java类集框架和数据结构(1)的内容 上一篇博文简介了java类集框架几大常见集合框架,这一篇博文主要分析一些接口特性以及性能优化. 一:List接口 List是最常见的数据结构了,主 ...

随机推荐

  1. jmeter测试流程整理

    背景 整理jmeter脚本编写流程,注意事项,常用组件,常见问题. 参看链接:https://www.cnblogs.com/pwj2lgx/p/10282422.html 参看:processOn思 ...

  2. 第十三篇 -- QMainWindow与QAction(新建-打开-保存)

    效果图: 添加了三个Action,分别是新建,打开,和保存,没有具体写相应的功能,只是提供了一个接口,可以自己写相应的功能.这次不仅将这些Action放在了工具栏,还将其添加到了菜单栏.方法同样是直接 ...

  3. TCP通信简单梳理

    一.什么是TCP协议 TCP协议是一种面向连接的可靠的通信协议,最重要的两个特点:连接.可靠. 二.TCP是如何进行通信的 TCP通过三次握手建立连接后客户端服务端的内核都分别开辟资源,这时候开始进行 ...

  4. (Opencv07)绘制边框

    (Opencv07)绘制边框 cv2.boundingRect(img) 这个函数可以获得一个图像的最小矩形边框一些信息 cv2.rectangle()可以画出该最小矩形边框 x, y ,w, h = ...

  5. Python3中datetime时区转换介绍与踩坑

    最近的项目需要根据用户所属时区制定一些特定策略,学习.应用了若干python3的时区转换相关知识,这里整理一部分记录下来. 下面涉及的几个概念及知识点: GMT时间:Greenwich Mean Ti ...

  6. frameset框架在.net网站中的小实现。

    一般我们生成网页,为减少代码的开发量,通常将不变的网页部分进行重用.通用为三种方法: 1.frameset框架 2.用户自定义控件 3.母版页(消耗资源大,不追叙) 通常1,2两种方法常用. 1.fr ...

  7. Drupal < 7.32 “Drupalgeddon” SQL注入漏洞(CVE-2014-3704)

    影响版本Drupal < 7.32

  8. ASP.NET Core下FreeSql的仓储事务

    ASP.NET Core下FreeSql的仓储事务 第一步:配置 Startup.cs 注入 引入包 dotnet add package FreeSql dotnet add package Fre ...

  9. Distance Queries 距离咨询 (LCA倍增模板)

    农夫约翰有N(2<=N<=40000)个农场,标号1到N.M(2<=M<=40000)条的不同的垂直或水平的道路连结着农场,道路的长度不超过1000.这些农场的分布就像下面的地 ...

  10. Top10 应用都在用的Android最新知识

    相信各位对Jetpack并不陌生,自从 Google 在 2018 年推出 Jetpack 之后,它就成为了 Android 未来发展的指向标. 作为一名安卓工程师,我们以前会经常吐槽Android碎 ...