Java多线程编程与并发处理
引言
在现代编程中,多线程和并发处理是提高程序运行效率和资源利用率的重要方法。Java提供了丰富的多线程编程支持,包括线程的创建与生命周期管理、线程同步与锁机制、并发库和高级并发工具等。本文将详细介绍这些内容,并通过表格进行总结和示范。
线程的创建与生命周期
使用Thread类
可以通过继承Thread
类来创建线程,并重写其run
方法。
public class MyThread extends Thread {public void run() {System.out.println("Thread is running.");}public static void main(String[] args) {MyThread thread = new MyThread();thread.start();}
}
使用Runnable接口
实现Runnable
接口并将其实例传递给Thread
对象也是创建线程的一种方式。
public class MyRunnable implements Runnable {public void run() {System.out.println("Runnable is running.");}public static void main(String[] args) {MyRunnable runnable = new MyRunnable();Thread thread = new Thread(runnable);thread.start();}
}
使用线程池
使用ExecutorService
可以创建和管理线程池。
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;public class ThreadPoolExample {public static void main(String[] args) {ExecutorService executor = Executors.newFixedThreadPool(5);for (int i = 0; i < 10; i++) {Runnable worker = new MyRunnable();executor.execute(worker);}executor.shutdown();}
}
线程的生命周期
线程有以下几种状态:
- 新建(New)
- 就绪(Runnable)
- 运行(Running)
- 等待/阻塞/休眠(Waiting/Blocked/Sleeping)
- 终止(Terminated)
线程同步与锁机制
同步方法
使用sychronized
关键字可以同步方法,确保同一时刻只有一个线程可以访问该方法。
public class SynchronizedExample {private int count = 0;public synchronized void increment() {count++;}public static void main(String[] args) {SynchronizedExample example = new SynchronizedExample();example.increment();}
}
同步块
同步块使用sychronized
关键字包围代码块,比同步方法更加灵活。
public class SynchronizedBlockExample {private int count = 0;private final Object lock = new Object();public void increment() {synchronized (lock) {count++;}}public static void main(String[] args) {SynchronizedBlockExample example = new SynchronizedBlockExample();example.increment();}
}
ReentrantLock
ReentrantLock
提供了更加灵活的锁机制。
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;public class ReentrantLockExample {private int count = 0;private final Lock lock = new ReentrantLock();public void increment() {lock.lock();try {count++;} finally {lock.unlock();}}public static void main(String[] args) {ReentrantLockExample example = new ReentrantLockExample();example.increment();}
}
并发库
Executor框架
Executor
框架是Java并发库的核心部分,简化了并发任务的执行。
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;public class ExecutorExample {public static void main(String[] args) {ExecutorService executor = Executors.newFixedThreadPool(2);for (int i = 0; i < 5; i++) {executor.submit(() -> {System.out.println(Thread.currentThread().getName() + " is executing task.");});}executor.shutdown();}
}
Future和Callable
Callable
接口表示一个可以返回结果的任务,Future
接口表示异步计算的结果。
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;public class FutureCallableExample {public static void main(String[] args) {ExecutorService executor = Executors.newCachedThreadPool();Callable<Integer> task = () -> {Thread.sleep(2000);return 123;};Future<Integer> future = executor.submit(task);try {System.out.println("Result: " + future.get());} catch (InterruptedException | ExecutionException e) {e.printStackTrace();} finally {executor.shutdown();}}
}
高级并发工具
CountDownLatch
CountDownLatch
允许一个或多个线程等待,直到其他线程完成一组操作。
import java.util.concurrent.CountDownLatch;public class CountDownLatchExample {public static void main(String[] args) throws InterruptedException {int count = 3;CountDownLatch latch = new CountDownLatch(count);for (int i = 0; i < count; i++) {new Thread(() -> {System.out.println(Thread.currentThread().getName() + " is running.");latch.countDown();}).start();}latch.await();System.out.println("All tasks completed.");}
}
CyclicBarrier
CyclicBarrier
允许一组线程互相等待,直到所有线程都到达一个屏障点,然后继续执行。
import java.util.concurrent.BrokenBarrierException;
import java.util.concurrent.CyclicBarrier;public class CyclicBarrierExample {public static void main(String[] args) {int count = 3;CyclicBarrier barrier = new CyclicBarrier(count, () -> {System.out.println("All threads arrived. Let's continue...");});for (int i = 0; i < count; i++) {new Thread(() -> {System.out.println(Thread.currentThread().getName() + " is waiting.");try {barrier.await();} catch (InterruptedException | BrokenBarrierException e) {e.printStackTrace();}}).start();}}
}
表格总结
线程的创建方法
创建方法 | 描述 | 示例 |
---|---|---|
继承Thread类 | 创建一个新的线程类,重写run 方法 | class MyThread extends Thread { public void run() { ... } } |
实现Runnable接口 | 创建一个实现Runnable 接口的类,实现run 方法 | class MyRunnable implements Runnable { public void run() { ... } } |
使用ExecutorService | 创建和管理线程池 | ExecutorService executor = Executors.newFixedThreadPool(5); |
线程同步方法
同步方法 | 描述 | 示例 |
---|---|---|
synchronized方法 | 同步整个方法,只允许一个线程访问 | public synchronized void increment() { ... } |
synchronized块 | 同步代码块,只允许一个线程访问指定代码块 | synchronized (lock) { ... } |
ReentrantLock | 显式锁机制,提供了更灵活的同步控制 | lock.lock(); try { ... } finally { lock.unlock(); } |
并发工具
工具 | 描述 | 示例 |
---|---|---|
CountDownLatch | 允许一个或多个线程等待,直到其他线程完成一组操作 | new CountDownLatch(count); |
CyclicBarrier | 允许一组线程互相等待,直到所有线程都到达屏障点 | new CyclicBarrier(count, Runnable); |
Executor框架 | 简化并发任务的执行和管理 | ExecutorService executor = Executors.newFixedThreadPool(2); |
Future和Callable | 表示异步计算和可返回结果的任务 | Future<Integer> future = executor.submit(task); |
应用场景与实践:生产者-消费者模型
生产者-消费者模型是多线程编程中的经典问题。该模型中,通过使用BlockingQueue
可以方便地实现线程之间的安全通信和协调,从而避免资源争用和死锁问题。
示例:生产者-消费者模型
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.BlockingQueue;public class ProducerConsumerExample {public static void main(String[] args) {BlockingQueue<Integer> queue = new ArrayBlockingQueue<>(10);// 生产者Runnable producer = () -> {int value = 0;while (true) {try {queue.put(value);System.out.println("Produced: " + value);value++;Thread.sleep(500); // 模拟生产时间} catch (InterruptedException e) {Thread.currentThread().interrupt();}}};// 消费者Runnable consumer = () -> {while (true) {try {int value = queue.take();System.out.println("Consumed: " + value);Thread.sleep(1000); // 模拟消费时间} catch (InterruptedException e) {Thread.currentThread().interrupt();}}};new Thread(producer).start();new Thread(consumer).start();}
}
在以上示例中,BlockingQueue
用作存储数据的共享缓冲区,生产者线程不断向队列中添加数据,而消费者线程从队列中取出数据进行处理。通过BlockingQueue
的阻塞特性,生产者和消费者在队列满或空时自动等待,从而实现线程间的协调。
表格总结
线程的创建方法
创建方法 | 描述 | 示例 |
---|---|---|
继承Thread类 | 创建一个新的线程类,重写run 方法 | class MyThread extends Thread { public void run() { ... } } |
实现Runnable接口 | 创建一个实现Runnable 接口的类,实现run 方法 | class MyRunnable implements Runnable { public void run() { ... } } |
使用ExecutorService | 创建和管理线程池 | ExecutorService executor = Executors.newFixedThreadPool(5); |
线程同步方法
同步方法 | 描述 | 示例 |
---|---|---|
synchronized方法 | 同步整个方法,只允许一个线程访问 | public synchronized void increment() { ... } |
synchronized块 | 同步代码块,只允许一个线程访问指定代码块 | synchronized (lock) { ... } |
ReentrantLock | 显式锁机制,提供了更灵活的同步控制 | lock.lock(); try { ... } finally { lock.unlock(); } |
并发工具
工具 | 描述 | 示例 |
---|---|---|
CountDownLatch | 允许一个或多个线程等待,直到其他线程完成一组操作 | new CountDownLatch(count); |
CyclicBarrier | 允许一组线程互相等待,直到所有线程都到达屏障点 | new CyclicBarrier(count, Runnable); |
Executor框架 | 简化并发任务的执行和管理 | ExecutorService executor = Executors.newFixedThreadPool(2); |
Future和Callable | 表示异步计算和可返回结果的任务 | Future<Integer> future = executor.submit(task); |
线程池与并发框架
Java并发编程中,线程池与并发框架是实现高效多线程的关键组件。线程池可以重复利用线程,减少线程创建和销毁的开销。而并发框架如java.util.concurrent
包则提供了丰富的并发工具。
线程池示例:固定大小线程池
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;public class FixedThreadPoolExample {public static void main(String[] args) {ExecutorService executor = Executors.newFixedThreadPool(3);for (int i = 0; i < 5; i++) {executor.submit(() -> {System.out.println(Thread.currentThread().getName() + " is executing task.");try {Thread.sleep(1000); // 模拟任务执行时间} catch (InterruptedException e) {Thread.currentThread().interrupt();}});}executor.shutdown();}
}
在此示例中,使用Executors.newFixedThreadPool(int)
方法创建一个固定大小的线程池,并提交多个任务供线程池执行。线程池能有效管理线程的创建和销毁,优化资源使用。
锁和同步机制
在多线程环境下,正确的锁和同步机制是防止数据竞争和确保数据一致性的关键。
ReentrantLock示例
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;public class ReentrantLockExample {private int count = 0;private final Lock lock = new ReentrantLock();public void increment() {lock.lock();try {count++;System.out.println(Thread.currentThread().getName() + " count: " + count);} finally {lock.unlock();}}public static void main(String[] args) {ReentrantLockExample example = new ReentrantLockExample();Runnable task = example::increment;for (int i = 0; i < 5; i++) {new Thread(task).start();}}
}
在上述示例中,ReentrantLock
用于显式锁机制,确保同一时刻只有一个线程能够访问共享数据。
结束语
本文详细介绍了Java中的多线程编程和并发处理,包括线程的创建与生命周期、线程同步与锁机制、并发库和高级并发工具等。通过代码示例和表格总结,希望您能更好地理解和应用Java的多线程编程,提高程序性能和资源利用率。
相关文章:
Java多线程编程与并发处理
引言 在现代编程中,多线程和并发处理是提高程序运行效率和资源利用率的重要方法。Java提供了丰富的多线程编程支持,包括线程的创建与生命周期管理、线程同步与锁机制、并发库和高级并发工具等。本文将详细介绍这些内容,并通过表格进行总结和…...
C++ 35 之 对象模型基础
#include <iostream> #include <string.h> using namespace std;class Students05{ public:// 只有非静态成员变量才算存储空间,其他都不算int s_a; // 非静态成员变量,算对象的存储空间double s_c;// 成员函数 不算对象的存储空间void f…...
PHP超级全局变量:功能、应用及最佳实践
PHP中的超级全局变量(Superglobal Variables)是预定义的数组,它们在脚本的全部作用域内都可以访问,无需使用global关键字。超级全局变量包含了关于请求、会话、服务器等各种信息,常见的有$_GET、$_POST、$_REQUEST、$_…...
python在windows创建的文件,换成linux系统格式
python在windows创建的文件,换成linux系统格式 dos2unix.exe的下载(下载的文件放入路径下:C:\Windows\System32) 链接:https://pan.baidu.com/s/10fC2tfvUtbh-axJ21cj_Xw?pwdm3zc 提取码:m3zc 批量修改文件格式 import subpr…...
最新区块链论文速读--CCF A会议 ICSE 2024 共13篇 附pdf下载 (2/2)
Conference:International Conference on Software Engineering (ICSE) CCF level:CCF A Categories:Software Engineering/System Software/Programming Languages Year:2024 Num:13 第1~7篇区块链文章请点击此处…...
C++ 34 之 单例模式
#include <iostream> #include <string.h> using namespace std;class King{// 公共的函数,为了让外部可以获取唯一的实例 public:// getInstance 获取单例 约定俗成static King* getInstance(){return true_king;}private: // 私有化// 构造函数设置为…...
SAP BW:传输转换源系统-源系统映射关系
最近有朋友再问问我源系统映射关系怎么配置,想着写一个怕以后忘了。 简单说下这个是干嘛的,其实就是配置一个源系统到目标系统的一个映射,这样传输的时候才知道传过来的数据源要变成目标系统的数据源。 比如下图,在开发环境&…...
React+TS前台项目实战(九)-- 全局常用组件弹窗Dialog封装
文章目录 前言Dialog公共弹窗组件1. 功能分析2. 代码详细注释3. 使用方式4. 效果展示 总结 前言 今天这篇主要讲全局公共弹窗Dialog组件封装,将用到上篇封装的模态框Modal组件。有时在前台项目中,偶尔要用到一两个常用的组件,如 弹窗&#x…...
利用视觉分析技术提升水面漂浮物、水面垃圾检测效率
随着城市化进程的加速和工业化的发展,水体污染问题日益严重,水面漂浮物成为水环境治理的一大难题。传统的水面漂浮物检测方法主要依赖人工巡查和简单的传感器检测,存在着效率低、准确率不高等问题。为了提升水面漂浮物检测的效率和准确性&…...
NFT 智能合约实战-快速开始(1)NFT发展历史 | NFT合约标准(ERC-721、ERC-1155和ERC-998)介绍
文章目录 NFT 智能合约实战-快速开始(1)NFT发展历史国内NFT市场国内NFT合规性如何获得NFT?如何查询NFT信息?在 OpenSea 上查看我们的 NFT什么是ERC721NFT合约标准ERC-721、ERC-1155和ERC-998 对比ERC721IERC721.sol 接口内容关于合约需要接收 ERC721 资产 onERC721Received…...
Linux知识整理说明
最近学校Linux课程刚刚结课,但还是有其他课程在继续。 所以接下来我会抽时间,根据笔记以及网络资料,整理和Linux相关的知识文档,各位可以后续留意. 完整的章目录我会先发出来,后续补充完整。 所有的内容会在 下周三(6…...
诊所管理系统哪家会好一点
随着医疗行业的快速发展和信息化进程的加速,诊所作为医疗服务的重要基层单位,其运营管理效率与服务质量的提升愈发依赖于现代化的管理工具。诊所管理系统应运而生,旨在通过集成化、智能化的技术手段,帮助诊所实现诊疗流程优化、资…...
前端根据权限生成三级路由
三级菜单和后端返回数组对比获取有权限的路由 数组: //后端返回的数组 const arr1 [sale.management, sale.order, sale.detail]; //前端路由 const arr2 [{path: "/sale-manage",redirect: "/sale-manage/sale-order/sale-list",name: sale…...
Databricks超10亿美元收购Tabular;Zilliz 推出 Milvus Lite ; 腾讯云支持Redis 7.0
重要更新 1. Databricks超10亿美元收购Tabular,Databricks将增强 Delta Lake 和 Iceberg 社区合作,以实现 Lakehouse 底层格式的开放与兼容([1] [2])。 2. Zilliz 推出 Milvus Lite 轻量级向量数据库,支持本地运行;Milvus Lite 复…...
算法day29
第一题 695. 岛屿的最大面积 本题解法:采用bfs的算法; 本题使用象限数组的遍历方法和定义布尔数组vis来遍历每一个元素的上下左右元素,防治被遍历的元素被二次遍历; 本题具体分析如上题故事,但是由于要求区域的最大面…...
车牌识别(附源代码)
完整项目已上传至github:End-to-end-for-chinese-plate-recognition/License-plate-recognition at master duanshengliu/End-to-end-for-chinese-plate-recognition GitHub 整体思路: 1.利用u-net图像分割得到二值化图像 2.再使用cv2进行边缘检测获得车牌区域坐…...
在VSCode中安装python
引言 Python 是一种广泛使用的高级编程语言,因其易学、易用、强大而受到欢迎。它由 Guido van Rossum 于 1991 年首次发布,并以简洁的语法和丰富的库生态系统而著称。 以下是 Python 的一些关键特点和优势: 关键特点 易于学习和使用&#x…...
StarkNet架构之L1-L2消息传递机制
文章目录 StarkNet架构之L1-L2消息传递机制L2 → L1消息L2 → L1消息结构L2 → L1消息哈希L1 → L2消息L1 → L2消息取消L1 → L2报文费用L1 → L2哈希额外资源StarkNet架构之L1-L2消息传递机制 原文地址:https://docs.starknet.io/architecture-and-concepts/network-archit…...
19.2 HTTP客户端-定制HTTP请求、调试HTTP、响应超时
1. 定制HTTP请求 如果需要对向服务器发送的HTTP请求做更多超越于默认设置的定制化。 client : http.Client{} 使用net/http包提供的导出类型Client,创建一个表示客户端的变量。request, err : http.NewRequest("GET", "https://ifconfig.io/ip&quo…...
KafkaQ - 好用的 Kafka Linux 命令行可视化工具
软件效果前瞻 ~ 鉴于并没有在网上找到比较好的linux平台的kafka可视化工具,今天为大家介绍一下自己开发的在 Linux 平台上使用的可视化工具KafkaQ 虽然简陋,主要可以实现下面的这些功能: 1)查看当前topic的分片数量和副本数量 …...
不愧是字节,图像算法面试真细致
这本面试宝典是一份专为大四、研三春招和研二暑假实习生准备的珍贵资料。 涵盖了图像算法领域的核心知识和常见面试题,包括卷积神经网络、实例分割算法、目标检测、图像处理等多个方面。不论你是初学者还是有经验的老手,都能从中找到实用的内容。 通过…...
14、C++中代码重用
1、C模板的主要作用是允许编写通用代码,即能够在不同数据类型或数据结构上工作而无需重复编写代码。通过模板,可以实现代码的复用性和灵活性,从而提高开发效率和程序的可维护性。 typename关键字: 在C中,typename关键…...
剖析框架代码结构的系统方法(下)
当面对Dubbo、Spring Cloud、Mybatis等开源框架时,我们可以采用一定的系统性的方法来快速把握它们的代码结构。这些系统方法包括对架构演进过程、核心执行流程、基础架构组成和可扩展性设计等维度的讨论。 在上一讲中,我们已经讨论了架构演进过程和核心执行流程这两个系统方法…...
C语言学习笔记之结构体(一)
目录 什么是结构体? 结构体的声明 结构体变量的定义和初始化 结构体成员的访问 结构体传参 什么是结构体? 在现实生活中的很多事物无法用单一类型的变量就能描述清楚,如:描述一个学生,需要姓名,年龄&a…...
MATLAB入门知识
目录 原教程链接:数学建模清风老师《MATLAB教程新手入门篇》https://www.bilibili.com/video/BV1dN4y1Q7Kt/ 前言 历史记录 脚本文件(.m) Matlab帮助系统 注释 ans pi inf无穷大 -inf负无穷大 i j虚数单位 eps浮点相对精度 0/&a…...
计算机网络(5) ARP协议
什么是ARP 地址解析协议,即ARP(Address Resolution Protocol),是根据IP地址获取物理地址的一个TCP/IP协议。主机发送信息时将包含目标IP地址的ARP请求广播到局域网络上的所有主机,并接收返回消息,以此确定…...
美团的 AI 面试有点简单
刷到一个美团的 AI 实习生的面试帖子,帖子虽然不长,但是把美团 AI 评测算法实习生面试的问题都po出来了。 单纯的看帖子中面试官提出的问题,并不是很难,大部分集中在考察AI项目和对AI模型的理解上,并没有过多的考察AI算…...
编程软件怎么给机器人编程:深入探索编程与机器人技术的融合
编程软件怎么给机器人编程:深入探索编程与机器人技术的融合 随着科技的飞速发展,机器人技术已经深入到我们生活的方方面面。而要让机器人按照我们的意愿执行任务,就需要借助编程软件对机器人进行编程。那么,编程软件究竟是如何给…...
unity2d Ugui--Image城市道路汽车行驶
目录 1.车辆生成与回收 2.路径点控制 3.车辆控制 1.车辆生成与回收 using System.Collections.Generic; using UnityEngine;public class RoadContr : MonoBehaviour {public WayPoint[] wayPoints; //出生点public Transform pare;[SerializeField]private Car[] fabCar;pu…...
【深度学习】【Prompt】使用GPT的一些提示词
f翻译论文用这个提示词: # 翻译规则## 翻译规则1 请在翻译这篇学术论文时,严格保留所有专业术语的原始英文表述,不要尝试将它们翻译成中文,而不是专业术语的部分,需要翻译为中文。保持所有文章引用格式和内容的完整无…...
隐藏wordpress文章/2020 惠州seo服务
内存(Memory)是计算机中最重要的部件之一,计算机运时的程序以及数据都依赖它进行存储。内存主要分为随机存储器(RAM),只读存储器(ROM)以及高速缓存(Cache)。仅仅雷达的原…...
武汉开发网站建设/第三方平台推广引流
01 TF&IDF概念TFTerm frequency:搜索文本中的各个词条在field文本中出现了多少次,出现次数越多,就越相关term在一个doc中出现的次数,出现的次数越多,分数越高IDFInverse document frequencry:搜索文本中的各个词条出现了多少次,出现的次数…...
零基础网站建设教学公司/如何在微信上做推广
以下实例中我们将数据表 runoob_tbl 数据导出到 /tmp/tutorials.txt 文件中: mysql> SELECT * FROM runoob_tbl -> INTO OUTFILE ‘/tmp/tutorials.txt’; 你可以通过命令选项来设置数据输出的指定格式,以下实例为导出 CSV 格式: mysql> SELECT…...
最好的wordpress 网站/关键词在线采集
文章目录1.准备工作2.基本使用3.声明浏览器对象4.访问页面5.查找节点单个节点多个节点6.节点交互7.动作链8.执行JavaScript9.获取节点信息获取属性读取文本值获取id、位置、标签名和大小10.切换Frame11.延时等待隐式等待显示等待12.前进和后退13.Cooikes14.选项卡管理15.异常处…...
外贸企业网站推广公司/广州公关公司
概要 题目来源链接:https://leetcode-cn.com/problems/majority-element/ 难度:简单 类型:链表 题目 给定一个大小为 n 的数组,找到其中的多数元素。多数元素是指在数组中出现次数大于 ⌊ n/2 ⌋ 的元素。 你可以假设数组是…...
泰兴做网站的公司/平台推广怎么做
久久的望, 长长的盼, 成熟的时候、落下。 是花、非她, 栽在了心口、 生根发芽。 不记得何时浇灌过泪水, 难想起几时为伊人憔悴, 漠然结果的时候, 听见了谁的心在碎。 飘啊、飞啊, 依偎在风的怀里…...