多线程顺序运行的 4 种方法

news2024/11/23 16:42:19

1、在子线程中通过join()方法指定顺序

通过join()方法使当前线程“阻塞”,等待指定线程执行完毕后继续执行。

举例:在线程thread2中,加上一句thread1.join(),其意义在于,当前线程2运行到此行代码时会进入阻塞状态,直到线程thread1执行完毕后,线程thread2才会继续运行,这就保证了线程thread1与线程thread2的运行顺序。

复制代码
public class ThreadJoinDemo {
    public static void main(String[] args) {
// 下面三行代码顺序可随意调整,程序运行结果不受影响,因为我们在子线程中通过“join()方法”已经指定了运行顺序。 thread3.start(); thread2.start(); thread1.start(); } static final Thread thread1 = new Thread(new Runnable() { @Override public void run() { System.out.println("打开冰箱!!!"); } }); static final Thread thread2 = new Thread(new Runnable() { @Override public void run() { try{ thread1.join(); }catch (InterruptedException e){ e.printStackTrace(); } System.out.println("拿出一瓶牛奶!!!"); } }); static final Thread thread3 = new Thread(new Runnable() { @Override public void run() { try{ thread2.join(); }catch (InterruptedException e){ e.printStackTrace(); } System.out.println("关上冰箱!!!"); } }); }
// 运行结果:
打开冰箱!!!
拿出一瓶牛奶!!!
关上冰箱!!!
复制代码

2、在主线程中通过join()方法指定顺序

简单说一下子线程与主线程的区别,子线程指的是发生在Thread内部的代码,主线程指的是发生在main函数中的代码。

我们可以在main函数中通过join()方法让主线程阻塞等待以达到指定顺序执行的目的。

复制代码
public class ThreadJoinDemo {
    public static void main(String[] args) throws InterruptedException {
        thread1.start();
        thread1.join();
        thread2.start();
        thread2.join();
        thread3.start();
    }
    static final Thread thread1 = new Thread(new Runnable() {
        @Override
        public void run() {
            System.out.println("打开冰箱!!!");
        }
    });
    static final Thread thread2 = new Thread(new Runnable() {
        @Override
        public void run() {
            System.out.println("拿出一瓶牛奶!!!");
        }
    });
    static final Thread thread3 = new Thread(new Runnable() {
        @Override
        public void run() {
            System.out.println("关上冰箱!!!");
        }
    });
}
// 输出结果:
打开冰箱!!!
拿出一瓶牛奶!!!
关上冰箱!!!
复制代码

3、通过倒数计时器CountDownLatch实现

CountDownLatch 通过计数器提供了更灵活的控制,只要检测到计数器为 0 当前线程就可以往下执行而不用管相应的 thread 是否执行完毕。

复制代码
public class ThreadCountDownLatchDemo {
</span><span style="color: rgba(0, 0, 255, 1)">private</span> <span style="color: rgba(0, 0, 255, 1)">static</span> CountDownLatch countDownLatch1 = <span style="color: rgba(0, 0, 255, 1)">new</span> CountDownLatch(1<span style="color: rgba(0, 0, 0, 1)">);

</span><span style="color: rgba(0, 0, 255, 1)">private</span> <span style="color: rgba(0, 0, 255, 1)">static</span> CountDownLatch countDownLatch2 = <span style="color: rgba(0, 0, 255, 1)">new</span> CountDownLatch(1<span style="color: rgba(0, 0, 0, 1)">);

</span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">static</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> main(String[] args) {
    </span><span style="color: rgba(0, 0, 255, 1)">final</span> Thread thread1 = <span style="color: rgba(0, 0, 255, 1)">new</span> Thread(<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> Runnable() {
        @Override
        </span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> run() {
            System.out.println(</span>"打开冰箱!"<span style="color: rgba(0, 0, 0, 1)">);
            <span style="color: rgba(255, 0, 0, 1)">countDownLatch1.countDown();</span>
        }
    });

    </span><span style="color: rgba(0, 0, 255, 1)">final</span> Thread thread2 = <span style="color: rgba(0, 0, 255, 1)">new</span> Thread(<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> Runnable() {
        @Override
        </span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> run() {
            </span><span style="color: rgba(0, 0, 255, 1)">try</span><span style="color: rgba(0, 0, 0, 1)"> {
                <span style="color: rgba(255, 0, 0, 1)">countDownLatch1.await();</span>
                System.out.println(</span>"拿出一瓶牛奶!"<span style="color: rgba(0, 0, 0, 1)">);
                <span style="color: rgba(255, 0, 0, 1)">countDownLatch2.countDown();</span>
            } </span><span style="color: rgba(0, 0, 255, 1)">catch</span><span style="color: rgba(0, 0, 0, 1)"> (InterruptedException e) {
                e.printStackTrace();
            }
        }
    });

    </span><span style="color: rgba(0, 0, 255, 1)">final</span> Thread thread3 = <span style="color: rgba(0, 0, 255, 1)">new</span> Thread(<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> Runnable() {
        @Override
        </span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> run() {
            </span><span style="color: rgba(0, 0, 255, 1)">try</span><span style="color: rgba(0, 0, 0, 1)"> {
                <span style="color: rgba(255, 0, 0, 1)">countDownLatch2.await();</span>
                System.out.println(</span>"关上冰箱!"<span style="color: rgba(0, 0, 0, 1)">);
            } </span><span style="color: rgba(0, 0, 255, 1)">catch</span><span style="color: rgba(0, 0, 0, 1)"> (InterruptedException e) {
                e.printStackTrace();
            }
        }
    });

    </span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">下面三行代码顺序可随意调整,程序运行结果不受影响</span>

thread3.start();
thread1.start();
thread2.start();
}
}
// 输出结果:
打开冰箱!
拿出一瓶牛奶!
关上冰箱!

复制代码

4、通过创建单一化线程池 newSingleThreadExecutor()实现

单线程化线程池 ( newSingleThreadExecutor ) 的优点,串行执行所有任务。

复制代码
public class ThreadPoolDemo {

static ExecutorService executorService = Executors.newSingleThreadExecutor();

</span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">static</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> main(String[] args) {
    </span><span style="color: rgba(0, 0, 255, 1)">final</span> Thread thread1 = <span style="color: rgba(0, 0, 255, 1)">new</span> Thread(<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> Runnable() {
        @Override
        </span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> run() {
            System.out.println(</span>"打开冰箱!"<span style="color: rgba(0, 0, 0, 1)">);
        }
    });

    </span><span style="color: rgba(0, 0, 255, 1)">final</span> Thread thread2 =<span style="color: rgba(0, 0, 255, 1)">new</span> Thread(<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> Runnable() {
        @Override
        </span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> run() {
            System.out.println(</span>"拿出一瓶牛奶!"<span style="color: rgba(0, 0, 0, 1)">);
        }
    });

    </span><span style="color: rgba(0, 0, 255, 1)">final</span> Thread thread3 = <span style="color: rgba(0, 0, 255, 1)">new</span> Thread(<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> Runnable() {
        @Override
        </span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> run() {
            System.out.println(</span>"关上冰箱!"<span style="color: rgba(0, 0, 0, 1)">);
        }
    });
    executorService.submit(thread1);
    executorService.submit(thread2);
    executorService.submit(thread3);
    executorService.shutdown();        </span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">使用完毕记得关闭线程池</span>

}

}
// 输出结果:
打开冰箱!
拿出一瓶牛奶!
关上冰箱!

复制代码

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/115745.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

FineReport填报报表常用属性方法

1、去除填报页面选中单元格时的黑色边框 // 加载结束事件 _g().curLGP.hideSelectFrame(); 2、 获取单元格焦点 预览填报报表时&#xff0c;希望页面加载完成后&#xff0c;自动将光标定位在某个控件中&#xff0c;可以直接编辑。 // 获取A2单元格 var cell _g().curLGP.getT…

风控模型算法

目录1 蚂蚁金服2 陆金所3 京东金融4 苏宁金融5 百度金融6 腾讯理财通7 宜信8 钱大掌柜9 万达金融10 网易理财11 美团金融主要是整理目前市面上的风控模型以及风控算法。1 蚂蚁金服 &#xff08;1&#xff09;对接第三方征信公司芝麻信用分&#xff0c;通过用户信用历史、行为偏…

echarts的xAxis和yAxis——x轴y轴以及网格线的详细配置

先看一下xAxis和yAxis配置的图表效果 下图详细的标注了图表中x轴y轴可见的内容 说明一下&#xff1a; x轴y轴在echarts配置项里&#xff0c;从内容上来说大体上没有太大区别&#xff0c;x轴能用的配置项y轴基本也可以用。 通过配置xAxis和yAxis可实现内容 坐标轴箭头的样式&…

Python量化交易01——构建基础策略

参考书目:深入浅出Python量化交易实战 量化交易是很早就想开的栏目了&#xff0c;之前没时间。现在正好放寒假&#xff0c;然后也找到了一本合适的书可以进行学习。 本次第一章就介绍一下简单的量化流程和一个简单的策略。 量化交易顾名思义就是用代码去验证交易策略是否赚钱…

【正点原子I.MX6U-MINI移植篇】Ubuntu-base根文件系统移植构建过程详解(四)

摘要&#xff1a;能不能在ARM板上运行Ubuntu呢&#xff1f;答案肯定是可以的&#xff0c;Ubuntu是Linux系统的一种&#xff0c;可以简单的将Ubuntu理解为一个根文件系统&#xff0c;和我们用busybox、buildroot制作的根文件系统一样。因此移植Ubuntu也就是将Ubuntu根文件系统移…

边缘计算概述

引用李开复在《ai 未来》书中说的&#xff0c;未来ai将会是中美双雄争霸的天下&#xff0c;美国虽然拥有创新的ai技术&#xff0c;重于开发&#xff0c;但现在ai已经到了可以实现落地到社会各个方面了&#xff0c;既然要落地就需要大量的测试和数据&#xff0c;只有中国的市场&…

我要是在学习 C 语言之前知道这些就好了

学习 C 语言好难啊。这门语言本身的基础知识并不是很难&#xff0c;但是“用 C 语言编程”需要用到各种知识&#xff0c;这些知识可没有那么容易掌握&#xff1a; C 语言在各个平台和操作系统上的行为有所差异&#xff0c;因此你需要了解平台&#xff1b; C 语言有许多编译器选…

SpringCloud+SpringCloud Alibaba(尚硅谷2020版)

文章目录1.传统单体架构和微服务架构的对比1.1传统单体架构1.1.1传统单体架构概述1.1.2单体架构的特点1.1.3单体架构的优点1.1.4单体架构的缺点1.2微服务架构1.2.1微服务架构概述1.2.2微服务架构的特点1.2.3微服务架构的优点1.2.4微服务架构的缺点2.SpringCloud简介3.SpringClo…

Service入门

Service入门 1.什么是Service 1.1手机中的Service案例 1.2为什么会有service&#xff1f; 由于手机的原因一个时刻只允许一个激活状态的Activity&#xff0c;其余的处于未激活 后台服务机制应运而生 1.3Service简介 四大组件之一没有UI界面&#xff0c;后台服务&#xff0c;长时…

Word处理控件Aspose.Words功能演示:在 Python 中将 Markdown 转换为 PDF

Aspose.Words 是一种高级Word文档处理API&#xff0c;用于执行各种文档管理和操作任务。API支持生成&#xff0c;修改&#xff0c;转换&#xff0c;呈现和打印文档&#xff0c;而无需在跨平台应用程序中直接使用Microsoft Word。此外&#xff0c; Aspose API支持流行文件格式处…

人物百度百科创建:建立人物百度百科都需要什么资料?

人物百度百科词条就像一张网络名片&#xff0c;词条上面的内容是非常具有权威性和公信力的。创建一个百度百科词条&#xff0c;可以帮助你很好地打造个人ip&#xff0c;尤其是在当今互联网时代&#xff0c;ip的打造对于个人的重要性是不言而喻的。 如果你想要提升自己的知名度…

2023年全国管理类联考综合试卷真题及解析

1.油价上涨5%后&#xff0c;加一箱油比原来多花20元&#xff0c;一个月后油价下降了4%&#xff0c;则加一箱油需要花( )钱 A.384元 B.401元 C.402.8元 D.403.2元 E.404元 2.已知甲、乙两公司的利润之比为3&#xff1a;4&#xff0c;甲、丙两公司的利润之比为1&am…

二硬脂酰磷脂酰乙醇胺-聚乙二醇-巯基吡啶 DSPE-PEG-OPSS;常用于脂质体的合成

DSPE-PEG-OPSS 、OPSS-PEG-DSPE 巯基吡啶聚乙二醇磷脂、磷脂聚乙二醇巯基吡啶 中文名称 &#xff1a;磷脂聚乙二醇巯基吡啶、巯基吡啶聚乙二醇磷脂 简称 &#xff1a;OPSS O-PEG-DSPE、DSPE-PEG-OPSS 外观 &#xff1a;白色液体、半固体或固体&#xff0c;取决于分子量。 …

Spring之底层架构核心概念-Environment

文章目录1.Environment作用2.用法2.1 systemEnvironment 和 systemProperties2.2 MutablePropertySources3.实际用法4.总结1.Environment作用 Environment&#xff1a;获取环境变量 2.用法 2.1 systemEnvironment 和 systemProperties public static void main(String[] ar…

【UE4 第一人称射击游戏】13-瞄准开火

上一篇&#xff1a; 【UE4 第一人称射击游戏】12-全自动步枪并显示剩余弹药量 本篇效果&#xff1a; 步骤&#xff1a; 1.打开“ThirdPersonCharacter”&#xff0c;添加一个骨架网格体组件 将其作为Mesh&#xff08;继承&#xff09;的子级 父项套接字选为“Weapon_Attach”…

2022需求最大的 8 种编程语言:Python第二,ta居榜首

一直以来&#xff0c;编程语言都是程序员非常关注的话题。虽然有超过200编程语言&#xff0c;但其中只有少数用于现实世界的行业。 2022年也快接近尾声&#xff0c;今年最受欢迎使用最多的语言有哪些呢&#xff1f; 从2021年10月到2022年11月&#xff0c;DevJobsScanner分析了…

国内葡萄酒行业数据浅析

大家好&#xff0c;这里是小安说网控。 葡萄酒是最为常见的果酒&#xff0c;在国内酒品市场上占据着一席之地。近年来&#xff0c;受整体经济环境影响&#xff0c;葡萄酒行业的各项数据都不甚理想。 今年&#xff0c;1-10月份&#xff0c;国内葡萄酒产值&#xff0c;无论是当期…

[ 代码审计篇 ] 代码审计案例详解(一) SQL注入代码审计案例

&#x1f36c; 博主介绍 &#x1f468;‍&#x1f393; 博主介绍&#xff1a;大家好&#xff0c;我是 _PowerShell &#xff0c;很高兴认识大家~ ✨主攻领域&#xff1a;【渗透领域】【数据通信】 【通讯安全】 【web安全】【面试分析】 &#x1f389;点赞➕评论➕收藏 养成习…

skywalking 快速入门

一、skywalking简介 1、skywalking介绍 Skywalking是一个国产的开源框架&#xff0c;2015年有吴晟个人开源&#xff0c;2017年加入Apache孵化器&#xff0c;国人开源的产品&#xff0c;主要开发人员来自于华为&#xff0c;2019年4月17日Apache董事会批准SkyWalking成为顶级项…

村政府小型网站

小型网站架构 编程工具&#xff0c;编程语言&#xff0c;编程细节 编程工具 idea最好的java项目编程工具&#xff0c;集合springboot框架。 编程语言 java,jsp,数据库表编程 编程细节 配置springboot&#xff0c;pom.xml相关配置文件&#xff0c;熟练使用idea以及相关目…