• 设为首页
  • 点击收藏
  • 手机版
    手机扫一扫访问
    迪恩网络手机版
  • 关注官方公众号
    微信扫一扫关注
    公众号

浅谈Java和Go的程序退出

原作者: [db:作者] 来自: [db:来源] 收藏 邀请

前言

今天在开发中对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协程也直接终止。

参考


鲜花

握手

雷人

路过

鸡蛋
该文章已有0人参与评论

请发表评论

全部评论

专题导读
上一篇:
go读取excel表格数据发布时间:2022-07-10
下一篇:
微软力挺 Go,宣布参与 Athens 项目和 GopherSource发布时间:2022-07-10
热门推荐
热门话题
阅读排行榜

扫描微信二维码

查看手机版网站

随时了解更新最新资讯

139-2527-9053

在线客服(服务时间 9:00~18:00)

在线QQ客服
地址:深圳市南山区西丽大学城创智工业园
电邮:jeky_zhao#qq.com
移动电话:139-2527-9053

Powered by 互联科技 X3.4© 2001-2213 极客世界.|Sitemap