Java---线程讲解(二)

文章目录

    • 1. Runnable接口
    • 2. 卖票案例
    • 3. 同步代码块解决数据安全问题
    • 4. 同步方法解决数据安全问题
    • 5. 线程安全的类
    • 6. Lock锁


1. Runnable接口

 1. 创建线程的另一种方法是声明一个实现Runnable接口的类,之后重写run()方法,然后可以分配类的实例,在创建Thread时作为参数传递,最后启动。

 2. 具体实现Runnable接口:(1) 定义一个MyRunnable实现Runnable接口。 (2) 在MyRunnable中重写run()方法。 (3) 创建MyRunnable类对象。 (4) 创建Thread类的对象,把MyRunnable对象作为构造方法的参数。 (5) 启动线程。

public class MyRunnable implements Runnable{@Overridepublic void run() {for(int i=0;i<100;i++){System.out.println(Thread.currentThread().getName()+":"+i);}}
}public class MyRunnableDemo {public static void main(String[] args) {//创建MyRunnable类对象MyRunnable my=new MyRunnable();//创建Thread类对象,把MyRunnable对象作为参数传进来//Thread(Runnable target)//Thread t1=new Thread(my);//Thread t2=new Thread(my);//Thread(Runnable target, String name)Thread t1=new Thread(my,"线程1");Thread t2=new Thread(my,"线程2");//启动线程t1.start();t2.start();}
}

在这里插入图片描述
 3. 多线程的实现方案有两种:(1) 继承Thread类。 (2) 实现Runnable接口。

  • 实现Runnable接口好处:避免了Java单继承的局限性;适合多个相同程序的代码去处理同一资源的情况,把线程和程序的代码、数据有效分离,较好地体现了面向对象的设计思想。

2. 卖票案例

 1. 需求和思路:

在这里插入图片描述

 2. 代码块:

public class SellTicket implements Runnable{//表示有100张票private int tickets=100;@Overridepublic void run() {while (true){if(tickets>0){System.out.println(Thread.currentThread().getName()+"正在出售第"+tickets+"张票");tickets--;}}}
}public class SellTicketDemo {public static void main(String[] args) {SellTicket st=new SellTicket();Thread t1=new Thread(st,"窗口1");Thread t2=new Thread(st,"窗口2");Thread t3=new Thread(st,"窗口3");t1.start();t2.start();t3.start();}
}

在这里插入图片描述
 3. 问题分析:看上面结果相同的票会出现三次,为什么呢?请参照下图理解,虽然加上了休眠时间,但是原理是一样的,都是线程抢占CPU执行权导致的。

在这里插入图片描述

3. 同步代码块解决数据安全问题

 1. 如何解决多线程安全问题:(1) 把多条语句操作共享数据的代码给锁起来,让任意时刻只能有一个线程执行即可。 (2) Java提供了同步代码块的方式来解决。

 2. 同步代码块格式:

在这里插入图片描述

 3. 代码块举例:

public class SellTicket implements Runnable{//表示有100张票private int tickets=100;private Object obj= new Object();@Overridepublic void run() {while (true){synchronized (obj) {if (tickets > 0) {System.out.println(Thread.currentThread().getName() + "正在出售第" + tickets + "张票");tickets--;}}}}
}public class SellTicketDemo {public static void main(String[] args) {SellTicket st=new SellTicket();Thread t1=new Thread(st,"窗口1");Thread t2=new Thread(st,"窗口2");Thread t3=new Thread(st,"窗口3");t1.start();t2.start();t3.start();}
}

在这里插入图片描述

 4. 同步的好处和弊端:(1) 好处:解决了多线程的数据安全问题。 (2) 弊端:当线程很多时,因为每个线程都会去判断同步上的锁,这是很耗费资源的,无形中会降低程序的运行效率。

4. 同步方法解决数据安全问题

 1. 同步方法:就是把synchronized关键字加到方法上。

 2. 格式:修饰符 synchronized 返回值类型 方法名(方法参数){ }

 3. 同步方法的锁对象:this

 4. 代码块举例:

public class SellTicket implements Runnable{//表示有100张票private int tickets=100;private Object obj= new Object();private int x=0;@Overridepublic void run() {while (true){if(x%2==0) {  //这里得是this,否则会出问题synchronized (this) {if (tickets > 0) {System.out.println(Thread.currentThread().getName() + "正在出售第" + tickets + "张票");tickets--;}}}else{sellticket();}x++;}}private synchronized void sellticket(){if (tickets > 0) {System.out.println(Thread.currentThread().getName() + "正在出售第" + tickets + "张票");tickets--;}}
}public class SellTicketDemo {public static void main(String[] args) {SellTicket st=new SellTicket();Thread t1=new Thread(st,"窗口1");Thread t2=new Thread(st,"窗口2");Thread t3=new Thread(st,"窗口3");t1.start();t2.start();t3.start();}
}

5. 线程安全的类

在这里插入图片描述

6. Lock锁

 1. 虽然我们可以理解同步代码块和同步方法的锁对象问题,但是我们并没有直接看到在哪里加上了锁,在哪里释放了锁,为了更清晰的表达如何加锁和释放锁,JDK5以后提供了一个新的锁对象Lock

 2. Lock实现提供比使用synchronized方法和语句可以获得更广泛的锁定操作。

 3. Lock中获得锁和释放锁的方法:void lock():获得锁。void unlock():释放锁。

 4. Lock是接口不能直接实例化,这里采用它的实现类ReentrantLock来实例化。

 5. 代码块举例:

public class SellTicket implements Runnable{//表示有100张票private int tickets=100;private Lock lock=new ReentrantLock();@Overridepublic void run(){while (true) {lock.lock();if (tickets > 0) {System.out.println(Thread.currentThread().getName() + "正在出售第" + tickets + "张票");tickets--;}lock.unlock();}}
}public class SellTicketDemo {public static void main(String[] args) {SellTicket st=new SellTicket();Thread t1=new Thread(st,"窗口1");Thread t2=new Thread(st,"窗口2");Thread t3=new Thread(st,"窗口3");t1.start();t2.start();t3.start();}
}

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

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

相关文章

基于remix+metamask+ganache的智能合约部署调用

在我们部署合约时为了让它更接近真实区块链去中心化体验&#xff0c;我们需要调用小狐狸&#xff08;Metamask&#xff09;来进行真实交易&#xff0c;而metamask里没有内置虚拟测试币&#xff0c;我们需要进行调用Ganache来添加带有虚拟测试币的账号。以上就是三者的关系&…

从 MLOps 到 LMOps 的关键技术嬗变

本文整理自 2023 年 9 月 3 日 QCon 全球软件开发大会 2023 北京站 —— 从 MLOps 到 LMOps 分论坛的同名主题演讲。 本次分享的内容结构如下&#xff1a; 从 MLOps 到 LMOps&#xff1b; MLOps 概述、挑战与解决方案&#xff1b; LMOps 实施挑战与关键技术&#xff08;大模…

[FPGA 学习记录] 快速开发的法宝——IP核

快速开发的法宝——IP核 文章目录 1 IP 核是什么2 为什么要使用 IP 核3 IP 核的存在形式4 IP 核的缺点5 Quartus II 软件下 IP 核的调用6 Altera IP 核的分类 在本小节当中&#xff0c;我们来学习一下 IP 核的相关知识。 IP 核在 FPGA 开发当中应用十分广泛&#xff0c;它被称为…

Java最全面试题专题---1、Java基础知识(2)

笔者有七八年的面试者经验&#xff0c;负责公司技术同学的社招和校招&#xff0c;近些年面试过三四百个技术同学&#xff0c;考虑接近年底这个时段&#xff0c;整理并更新一些以往的面试经验&#xff0c;希望同学们跳槽能有个更好的工作&#xff0c;如有需要的同学可以关注下笔…

Jenkins安装

环境 Ubuntu&#xff0c; 其他平台查看官方文档 步骤 安装jdk sudo apt-get install openjdk-8-jdk 安装Jenkins first add the key to your system wget -q -O - https://pkg.jenkins.io/debian/jenkins.io.key | sudo apt-key add -Then add a Jenkins apt repository …

使用Golang构建高性能网络爬虫

目录 一、Golang的特点 二、构建网络爬虫的步骤 三、关键技术和注意事项 使用协程进行并发处理 使用通道进行协程间的通信 合理控制并发数和处理速度 遵守网站使用协议和法律法规 防止被网站封禁或限制访问 优化网页解析和数据处理 异常处理和错误处理 日志记录和监控…

Flink入门之部署(二)

三种部署模式 standalone集群&#xff0c;会话模式部署&#xff1a;先启动flink集群 web UI提交shell命令提交&#xff1a;bin/flink run -d -m hadoop102:8081 -c com.atguigu.flink.deployment.Flinke1_NordCount./Flink-1.0-SNAPSHOT.jar --hostname hadoop102 --port 8888 …

vmware虚拟机17 安装macos14过程及问题处理亲测

前期准备 1、可引导可虚拟机安装的macOS Sonoma 14 ISO镜像安装文件 我找到得地址&#xff0c;下载自行解决啦 2、VMware虚拟机应用软件 官网下载就好&#xff0c;搜个码搞定 3、解锁工具macOS Unlocker 开始安装&#xff1a; 1、打开VMware软件&#xff0c;新建一个系统…

API集锦:免费好用的API接口

通用文字识别OCR&#xff1a;多场景、多语种、高精度的整图文字检测和识别服务&#xff0c;多项指标行业领先&#xff0c;可识别中、英、日、韩、法、德多种语言。 二维码识别OCR&#xff1a;对图片中的二维码、条形码进行检测和识别&#xff0c;返回存储的文字内容。 手机号…

Bert-vits2新版本V2.1英文模型本地训练以及中英文混合推理(mix)

中英文混合输出是文本转语音(TTS)项目中很常见的需求场景&#xff0c;尤其在技术文章或者技术视频领域里&#xff0c;其中文文本中一定会夹杂着海量的英文单词&#xff0c;我们当然不希望AI口播只会念中文&#xff0c;Bert-vits2老版本(2.0以下版本)并不支持英文训练和推理&…

完整方案开放下载!详解中国移动《通信网络中量子计算应用研究报告》

8月30日&#xff0c;中国移动在第四届科技周暨战略性新兴产业共创发展大会上重磅发布了《通信网络中量子计算应用研究报告》。 玻色量子作为中国移动在光量子计算领域的唯一一家合作企业兼战投企业&#xff0c;在量子计算应用于通信行业达成了深入合作&#xff0c;并在5G天线多…

干货分享|300平米A级机房设计方案

本方案中XXX计算机中心机房建设工程&#xff0c;是XXX的数据中心&#xff0c;机房位于建筑的X层&#xff0c;计算机机房面积300㎡。采购设备以及装修工艺主要用于XXX所属计算机机房装修工程。 考虑到中心机房投资大、使用周期长&#xff0c;而业主业务发展快&#xff0c;现代技…

十二 动手学深度学习v2计算机视觉 ——目标检测

文章目录 锚框目标检测常用算法RCNNFast RCNNFaster RCNNSSD 单发多框检测YOLO 锚框 一类目标检测算法&#xff1a;以图像的每个像素为中心生成不同形状的锚框&#xff0c;并赋予标号&#xff0c;每个锚框作为一个样本进行训练。在预测时&#xff0c;使用NMS来去掉冗余的预测。…

空间地图GIS基础

关注微信公众号掌握更多技术动态 --------------------------------------------------------------- 一、GIS基本概念 地理信息系统&#xff08;Geographic Informaiton System, GIS&#xff09;是一个可以建立、浏览、查询、分析地理空间数据的软件系统&#xff0c;其功能小…

利用 Python 进行数据分析实验(六)

一、实验目的 使用Python解决问题 二、实验要求 自主编写并运行代码&#xff0c;按照模板要求撰写实验报告 三、实验步骤 假设有两个txt文件&#xff0c;内容如下&#xff1a; seg1.txtseg2.txt 将这两个文件中的内容根据id(即前面的编号)合并为如下内容&#xff0c;并存…

Vue+ElementUI实现输入框日期框下拉框动态展示

1.首先根据后端返回的数据格式获取类型从而展示对应的框 // fieIdName label名字 // fieIdType 类型 1和4是输入框 2日期框 3日期时间框 5下拉框 // isRequired 1必填 0不必填 // fieIdTypeRange 存放一部分的下拉框的值 需要拿到数据后转成下拉框所需要的格式这种数据…

【AI】Pytorch神经网络分类初探

Pytorch神经网络分类初探 1.数据准备 环境采用之前创建的Anaconda虚拟环境pytorch&#xff0c;为了方便查看每一步的返回值&#xff0c;可以使用Jupyter Notebook来进行开发。首先把需要的包导入进来 import torch from torch import nn from torch.utils.data import DataL…

【RHCE】openlab搭建web网站

网站需求&#xff1a; 1、基于域名 www.openlab.com 可以访问网站内容为 welcome to openlab!!! 增加映射 [rootlocalhost ~]# vim /etc/hosts 创建网页 [rootlocalhost ~]# mkdir -p /www/openlab [rootlocalhost ~]# echo welcome to openlab > /www/openlab/index.h…

利用法线贴图渲染逼真的3D老虎模型

在线工具推荐&#xff1a; 3D数字孪生场景编辑器 - GLTF/GLB材质纹理编辑器 - 3D模型在线转换 - Three.js AI自动纹理开发包 - YOLO 虚幻合成数据生成器 - 三维模型预览图生成器 - 3D模型语义搜索引擎 当谈到游戏角色的3D模型风格时&#xff0c;有几种不同的风格&#xf…

傅里叶变换在图像中的应用

1.图像增强与图像去噪 绝大部分噪音都是图像的高频分量&#xff0c;通过低通滤波器来滤除高频——噪声; 边缘也是图像的高频分量&#xff0c;可以通过添加高频分量来增强原始图像的边缘&#xff1b; 2.图像分割之边缘检测 提取图像高频分量 3.图像特征提取&#xff1a; 形状特…