多线程的五种“打开”方式
1 概念
1.1 线程是什么??
线程(Thread)是计算机科学中的一个基本概念,它是进程(Process)中的一个执行单元,负责执行程序的指令序列。线程是操作系统能够进行调度和执行的最小单位。在多任务操作系统中,多个线程可以在同一个进程内并发执行,共享进程的资源。
{
假设你正在厨房中准备晚餐,这个过程中有多个线程在运行,每个线程代表一个不同的烹饪任务。这些线程可以同时执行,以加速整个烹饪过程,就像多线程在计算机程序中一样。
主厨线程:这个线程负责协调整个烹饪过程。主厨线程制定了食谱和指导其他线程如何协同工作。
切菜线程:这个线程负责将食材切成适当的大小和形状。它可以在切菜板上进行多个切割任务,以提高效率。
炉灶线程:这个线程负责在炉灶上烹饪不同的菜肴。例如,一个线程可以煮汤,另一个线程可以煎肉,它们可以同时工作,以节省时间。
烤箱线程:如果你需要烤一道菜,那么烤箱线程可以负责在烤箱中烘烤食物,同时其他线程继续处理其他任务。
洗碗线程:一旦完成烹饪,就有一个线程负责洗碗和清理厨房。这个线程可以与其他线程并发运行,以确保整个晚餐流程的顺利结束。
在这个例子中,每个线程都代表一个不同的烹饪任务,它们可以并行工作,以提高烹饪效率,就像多线程在计算机程序中允许不同任务并发执行一样
}
1.2 为什么要使用线程??
1 “并发编程”成为“刚需”
单核CPU的发展遇到了瓶颈,想要提高算力,就需要多核CPU。而并发编程能够充分利用多核CPU资源;
有些任务场景需要“等待IO”,为了让等待的时间去做一些其他工作,也需要使用到并发编程。
2. 虽然进程也能够实现并发编程,但是线程比进程更加轻量级。
- 创建线程比创建进程更快.
- 销毁线程比销毁进程更快.
- 调度线程比调度进程更快.
1.3 进程和线程的区别??
- 进程是包含线程的。每个进程至少有一个线程的存在,也就是主线程;
- 进程和线程之间不共享内存空间。同一个进程的线程之间共享同一内存空间;
- 进程是系统分配资源的最小单位,线程是操作系统调度的最小单位;
- 进程是相互独立的,一个进程的崩溃通常不会影响其他进程。线程之间更密切相关,一个线程的错误可能会影响到同一进程中的其他线程。
- 创建和销毁进程通常比线程昂贵,因为进程需要分配和释放独立的内存空间和资源。线程的创建和销毁通常更快,因为它们共享进程的资源,不需要分配独立的内存空间。
1.4 Java的线程和操作系统的线程的区别??
- 线程是操作系统中的概念. 操作系统内核实现了线程这样的机制, 并且对用户层提供了一些 API 供用户使用(例如 Linux 的 pthread 库).
- Java 标准库中 Thread 类可以视为是对操作系统提供的 API 进行了进一步的抽象和封装.
2 感受多线程代码
多线程和普通程序最大的区别就是每个线程都是独立的执行流 多线程之间是并发执行的。
public class ThreadDemo {private static class MyThread extends Thread{@Overridepublic void run() {Random random = new Random();while (true){// 打印主线程名称System.out.println(Thread.currentThread().getName());try {Thread.sleep(random.nextInt(10));//随机停止运行0-9秒} catch (InterruptedException e) {e.printStackTrace();}}}}public static void main(String[] args) {MyThread t1 = new MyThread();MyThread t2 = new MyThread();MyThread t3 = new MyThread();//启动并创建线程工作t1.start();t2.start();t3.start();//主线程工作Random random = new Random();while (true){// 打印主线程名称System.out.println(Thread.currentThread().getName());try {Thread.sleep(random.nextInt(10));//随机停止运行0-9秒} catch (InterruptedException e) {e.printStackTrace();}}}
}
结果:

我们可以使用JDK提供的jconsole命令观察线程(在jdk的bin目录下面)


3 创建线程的“五种”方式
方法1 继承Thread类
public class ThreadDemo1 {static class MyThread extends Thread{//重写run方法 run描述该线程要干的活是什么@Overridepublic void run() {System.out.println("我是一个线程 hello thread!");}//run方法执行完毕后 新的这个线程就会被销毁}public static void main(String[] args) {Thread thread = new MyThread();//thread类不需要任何包??为什么还有哪些我们见过的 出现这种情况 java.lang包下面的是不用导包的 比如string stirngbuilderthread.start();//线程中的启动方法 start创建了一个新线程 有新线程来执行run方法}
}
方法2 实现Runnable 接口
// Runnable 作用就是描述一个“要执行的任务” run方法就是任务的执行细节
class MyRunnable implements Runnable{@Overridepublic void run() {System.out.println("hello thread-runnable");}
}public class ThreadDemo2 {public static void main(String[] args) {// new Runnable就是描述一个任务MyRunnable runnable = new MyRunnable();//然后将这个任务交给线程来执行Thread thread = new Thread(runnable);thread.start();thread.run();/** thread.run()是在当前线程中执行线程的任务,没有创建新的线程,不实现并发。thread.start()创建一个新的线程,并在新线程中执行线程的任务,实现了多线程并发。通常应该使用thread.start()来启动线程*/}
}
首先对比一下上面两种方法:
- 继承 Thread 类, 直接使用 this 就表示当前线程对象的引用.
- 实现 Runnable 接口, this 表示的是 MyRunnable 的引用. 需要使用 Thread.currentThread()
后面的方法都是前两者的“变形”:
方法3 匿名内部类创建 Thread 子类对象
//使用匿名内部类来实现线程
public class ThreadDemo3 {public static void main(String[] args) {Thread t = new Thread() {@Overridepublic void run() {System.out.println("匿名内部类实现thread");}};t.start();}
}
方法4 匿名内部类创建 Runnable 子类对象
//使用匿名内部类
public class ThreadDemo4 {public static void main(String[] args) {Thread t = new Thread(new Runnable() {@Overridepublic void run() {System.out.println("实现runnable-匿名内部类");}});t.start();}
}
方法5 lambda 表达式创建 Runnable 子类对象
//lambda
public class ThreadDemo5 {public static void main(String[] args) {Thread t = new Thread(() -> {System.out.println("hello thread");});t.start();}
}
相关文章:
多线程的五种“打开”方式
1 概念 1.1 线程是什么?? 线程(Thread)是计算机科学中的一个基本概念,它是进程(Process)中的一个执行单元,负责执行程序的指令序列。线程是操作系统能够进行调度和执行的最小单位。…...
信息熵 条件熵 交叉熵 联合熵 相对熵(KL散度) 互信息(信息增益)
粗略版快速总结 条件熵 H ( Q ∣ P ) 联合熵 H ( P , Q ) − H ( P ) 条件熵H(Q∣P)联合熵H(P,Q)−H(P) 条件熵H(Q∣P)联合熵H(P,Q)−H(P) 信息增益 I ( P , Q ) H ( P ) − H ( P ∣ Q ) H ( P ) H ( Q ) − H ( P , Q ) 信息增益 I(P,Q)H(P)−H(P∣Q)H(P)H(Q)-H(P,Q) 信息…...
Fiddler Response私人订制
在客户端接口的测试中,我们经常会需要模拟各种返回状态或者特定的返回值,常见的是用Fiddler模拟各种请求返回值场景,如重定向AutoResponder、请求拦截修改再下发等等。小编在近期的测试中遇到的一些特殊的请求返回模拟的测试场景,…...
【德哥说库系列】-ASM管理Oracle 19C单实例部署
📢📢📢📣📣📣 哈喽!大家好,我是【IT邦德】,江湖人称jeames007,10余年DBA及大数据工作经验 一位上进心十足的【大数据领域博主】!😜&am…...
手写一个简单爬虫--手刃豆瓣top250排行榜
#拿到页面面源代码 request #通过re来提取想要的有效信息 re import requests import re url"https://movie.douban.com/top250"headers{"user-agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/11…...
【word密码】如何限制word文件中部分内容?
Word文件中有一部分内容不想他人编辑,我们可以设置限制编辑,可以对一部分内容设置限制编辑,具体方法如下: 我们将需要将可以编辑的地方选中,然后打开限制编辑功能 然后勾选限制编辑设置界面中的【限制编辑】和【每个人…...
spring 自定义类型转换-ConverterRegistry
1背景介绍 一个应用工程里面,一遍会涉及到很多的模型转换,如DTO模型转DO模型,DO模型转DTO, 或者Request转DTO模型,总的来说,维护起来还是相对比较复杂。每涉及一个转换都需要重新写对应类的get或者set方法,…...
springboot实现发送短信验证码
目录 一、选择并注册短信服务提供商: 二、添加依赖: 三、配置短信服务信息: 四、编写发送短信验证码的方法: 五、调用发送短信验证码的方法: 一、选择并注册短信服务提供商: 1、选择一个可靠的短信服…...
2024王道408数据结构P144 T18
2024王道408数据结构P144 T18 思考过程 首先还是先看题目的意思,让我们在中序线索二叉树里查找指定结点在后序的前驱结点,这题有一点难至少对我来说…我讲的不清楚理解一下我做的也有点糊涂。在创建结构体时多两个变量ltag和rtag,当ltag0时…...
在windows下安装配置skywalking
1.下载地址 Downloads | Apache SkyWalkinghttp://skywalking.apache.org/downloads/ 2.文件目录说明 将文件解压后,可看到agent和bin目录: Agent:作为探针,安装在服务器端,进行数据采集和上报。 Config:…...
关于大模型参数微调的不同方法
Adapter Tuning 适配器模块(Adapter Moudle)可以生成一个紧凑且可扩展的模型;每个任务只需要添加少量可训练参数,并且可以在不重新访问之前任务的情况下添加新任务。原始网络的参数保持不变,实现了高度的参数共享 Pa…...
方法的引用第一版(method reference)
1、体验方法引用 在使用Lambda表达式的时候,我们实际上传递进去的代码就是一种解决方案:拿参数做操作那么考虑一种情况:如果我们在Lanbda中所指定的操作方案,已经有地方存在相同方案,那是否还有必要再重复逻辑呢&#…...
Android DataBinding 基础入门(学习记录)
目录 一、DataBinding简介二、findViewById 和 DataBinding 原理及优缺点1. findViewById的优缺点2. DataBinding的优缺点 三、Android mvvm 之 databinding 原理1. 简介和三个主要的实体DataViewViewDataBinding 2.三个功能2.1. rebind 行为2.2 observe data 行为2.3 observe …...
spring 错误百科
一、使用Spring出错根源 1、隐式规则的存在 你可能忽略了 Sping Boot 中 SpringBootApplication 是有一个默认的扫描包范围的。这就是一个隐私规则。如果你原本不知道,那么犯错概率还是很高的。类似的案例这里不再赘述。 2、默认配置不合理 3、追求奇技淫巧 4、…...
OpenCV基本操(IO操作,读取、显示、保存)
图像的IO操作,读取和保存方法 1.1 API cv.imread()参数: 要读取的图像 读取图像的方式: cv.IMREAD*COLOR:以彩色模式加载图像,任何图像的图像的透明度都将被忽略。这是默认参数 标志: 1 cv.IMREAD*GRAYSCALE :以…...
1.快速搭建Flask项目
一.Pear Admin Flask 官网文档:http://www.pearadmin.com/doc/index.html 1.1下载安装 # 下 载 git clone https://gitee.com/pear-admin/pear-admin-flask# 安 装 pip install -r requirements.txt1.2修改配置 applications下的config.py docker运行的修改dockerdata/conf…...
编程题四大算法思想(三)——贪心法:找零问题、背包问题、任务调度问题、活动选择问题、Prim算法
文章目录 贪心法找零问题(change-making problem)贪心算法要求基本思想适合求解问题的特征 背包问题0/1背包问题0/1背包问题——贪心法 分数背包问题 任务调度问题活动选择问题活动选择——贪心法最早结束时间优先——最优性证明 Prim算法 贪心法 我在当…...
core dump管理在linux中的前世今生
目录 一、什么是core dump? 二、coredump是怎么来的? 三、怎么限制coredump文件的产生? ulimit 半永久限制 永久限制 四、从源码分析如何对coredump文件的名字和路径管理 命名 管理 一些问题的答案 1、为什么新的ubuntu不能产生c…...
Springboot整合knife4j配置swagger教程-干货
开启swagger文档,直接上教程。 第一步:引入依赖 <!--swagger 依赖--><dependency><groupId>com.github.xiaoymin</groupId><artifactId>knife4j-spring-boot-starter</artifactId><version>3.0.3</version></d…...
C++ 中的 Pimpl 惯用法
C 中的 Pimpl 惯用法 介绍 Pimpl(Pointer to Implementation)是一种常见的 C 设计模式,用于隐藏类的实现细节,从而减少编译依赖和提高编译速度。本文将通过一个较为复杂的例子,展示如何使用智能指针(如 s…...
日语AI面试高效通关秘籍:专业解读与青柚面试智能助攻
在如今就业市场竞争日益激烈的背景下,越来越多的求职者将目光投向了日本及中日双语岗位。但是,一场日语面试往往让许多人感到步履维艰。你是否也曾因为面试官抛出的“刁钻问题”而心生畏惧?面对生疏的日语交流环境,即便提前恶补了…...
反向工程与模型迁移:打造未来商品详情API的可持续创新体系
在电商行业蓬勃发展的当下,商品详情API作为连接电商平台与开发者、商家及用户的关键纽带,其重要性日益凸显。传统商品详情API主要聚焦于商品基本信息(如名称、价格、库存等)的获取与展示,已难以满足市场对个性化、智能…...
逻辑回归:给不确定性划界的分类大师
想象你是一名医生。面对患者的检查报告(肿瘤大小、血液指标),你需要做出一个**决定性判断**:恶性还是良性?这种“非黑即白”的抉择,正是**逻辑回归(Logistic Regression)** 的战场&a…...
大数据零基础学习day1之环境准备和大数据初步理解
学习大数据会使用到多台Linux服务器。 一、环境准备 1、VMware 基于VMware构建Linux虚拟机 是大数据从业者或者IT从业者的必备技能之一也是成本低廉的方案 所以VMware虚拟机方案是必须要学习的。 (1)设置网关 打开VMware虚拟机,点击编辑…...
前端导出带有合并单元格的列表
// 导出async function exportExcel(fileName "共识调整.xlsx") {// 所有数据const exportData await getAllMainData();// 表头内容let fitstTitleList [];const secondTitleList [];allColumns.value.forEach(column > {if (!column.children) {fitstTitleL…...
postgresql|数据库|只读用户的创建和删除(备忘)
CREATE USER read_only WITH PASSWORD 密码 -- 连接到xxx数据库 \c xxx -- 授予对xxx数据库的只读权限 GRANT CONNECT ON DATABASE xxx TO read_only; GRANT USAGE ON SCHEMA public TO read_only; GRANT SELECT ON ALL TABLES IN SCHEMA public TO read_only; GRANT EXECUTE O…...
C# 类和继承(抽象类)
抽象类 抽象类是指设计为被继承的类。抽象类只能被用作其他类的基类。 不能创建抽象类的实例。抽象类使用abstract修饰符声明。 抽象类可以包含抽象成员或普通的非抽象成员。抽象类的成员可以是抽象成员和普通带 实现的成员的任意组合。抽象类自己可以派生自另一个抽象类。例…...
工业自动化时代的精准装配革新:迁移科技3D视觉系统如何重塑机器人定位装配
AI3D视觉的工业赋能者 迁移科技成立于2017年,作为行业领先的3D工业相机及视觉系统供应商,累计完成数亿元融资。其核心技术覆盖硬件设计、算法优化及软件集成,通过稳定、易用、高回报的AI3D视觉系统,为汽车、新能源、金属制造等行…...
ArcGIS Pro制作水平横向图例+多级标注
今天介绍下载ArcGIS Pro中如何设置水平横向图例。 之前我们介绍了ArcGIS的横向图例制作:ArcGIS横向、多列图例、顺序重排、符号居中、批量更改图例符号等等(ArcGIS出图图例8大技巧),那这次我们看看ArcGIS Pro如何更加快捷的操作。…...
Python ROS2【机器人中间件框架】 简介
销量过万TEEIS德国护膝夏天用薄款 优惠券冠生园 百花蜂蜜428g 挤压瓶纯蜂蜜巨奇严选 鞋子除臭剂360ml 多芬身体磨砂膏280g健70%-75%酒精消毒棉片湿巾1418cm 80片/袋3袋大包清洁食品用消毒 优惠券AIMORNY52朵红玫瑰永生香皂花同城配送非鲜花七夕情人节生日礼物送女友 热卖妙洁棉…...
