Java多线程之Semaphore实现信号灯

现在我来讲解一下"Java多线程之Semaphore实现信号灯"的完整攻略。在Java多线程编程中,Semaphore可以用来控制多个线程需要访问的资源的数量,Semaphore允许多个线程同时访问某一个资源,但需要限制其同时访问的数量。

Semaphore的基本用法

Semaphore的构造方法:

public Semaphore(int permits)

其中permits表示同时能够访问某一个资源的线程数目。

Semaphore的两个基本方法:

public void acquire() throws InterruptedException
public void release()

其中acquire方法会获取Semaphore的许可,如果没有足够的许可,则会进入等待状态;release方法会释放Semaphore的许可。

Semaphore的应用场景:
Semaphore常用于多个共享资源的互斥使用。例如,读写线程都要访问同一个文件,但是需要限制同时访问该文件的线程数量。

示例一:访问共享资源

下面我们以读写线程访问文件的示例来说明Semaphore的应用。

import java.util.concurrent.Semaphore;

public class ReadWriteFile {
    private Semaphore readSemaphore = new Semaphore(5); // 读许可证
    private Semaphore writeSemaphore = new Semaphore(1); // 写许可证

    public void read() throws InterruptedException {
        readSemaphore.acquire(); // 获取读许可证
        // 读文件
        Thread.sleep(1000);
        System.out.println(Thread.currentThread().getName() + "读了文件");
        readSemaphore.release(); // 释放读许可证
    }

    public void write() throws InterruptedException {
        writeSemaphore.acquire(); // 获取写许可证
        // 写文件
        Thread.sleep(2000);
        System.out.println(Thread.currentThread().getName() + "写了文件");
        writeSemaphore.release(); // 释放写许可证
    }

    public static void main(String[] args) throws InterruptedException {
        ReadWriteFile rwf = new ReadWriteFile();
        // 多个读线程
        for (int i = 0; i < 10; i++) {
            new Thread(() -> {
                try {
                    rwf.read();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }, "reader " + i).start();
        }
        // 一个写线程
        new Thread(() -> {
            try {
                rwf.write();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }, "writer").start();
    }
}

上述代码中,read和write方法表示读和写文件。在构造方法中,我们定义了读许可证和写许可证,读许可证可以有5个,写许可证只能有一个。在读文件时,需要读许可证,如果没有足够的读许可证,则线程进入等待状态;在写文件时,需要写许可证,如果没有写许可证,则线程进入等待状态。

上述代码中,我们同时创建10个读线程和1个写线程。根据定义,每次最多只能有5个读线程同时访问文件,只能有一个线程写文件。我们可以运行代码,并观察10个读线程和1个写线程的执行情况。

示例二:限制系统资源

下面我们以限制系统资源数量的示例来说明Semaphore的应用。

import java.util.concurrent.Semaphore;

public class SemaphoreTest {
    public static void main(String[] args) {
        Semaphore semaphore = new Semaphore(2); // 限制系统中最多只能有两个进程并发执行
        // 创建10个线程模拟进程
        for (int i = 0; i < 10; i++) {
            new Thread(() -> {
                try {
                    semaphore.acquire(); // 获取许可证
                    System.out.println(Thread.currentThread().getName() + "获得许可证,开始执行");
                    Thread.sleep(1000); // 模拟进程执行的时间
                    semaphore.release(); // 释放许可证
                    System.out.println(Thread.currentThread().getName() + "释放许可证,执行结束");
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }, "Process " + i).start(); // 线程命名为Process0,Process1....Process9
        }
    }
}

上述代码中,Semaphore的初始值为2,表示系统中最多只能有两个进程并发执行。在创建10个线程模拟进程时,每个线程首先获取许可证,如果已经有2个线程在执行,则该线程进入等待状态。当其他线程释放许可证时,当前线程获取到许可证,开始执行进程操作。

上述代码中,我们可以运行代码,并观察10个线程的执行情况。

总结

通过本文的讲解,我们了解了Semaphore在多线程编程中的应用,Semaphore可以用来控制线程对资源的访问数量。Semaphore通过acquire方法获取许可证,通过release方法释放许可证。

在实际应用中,我们可以用Semaphore来实现读写锁、限制系统资源并发执行的数量等。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:Java多线程之Semaphore实现信号灯 - Python技术站

(0)
上一篇 2023年5月18日
下一篇 2023年5月18日

相关文章

  • java怎么创建目录(删除/修改/复制目录及文件)代码实例

    要在Java中创建、删除、修改和复制目录及文件,可以使用Java中自带的File类和方法。下面将在markdown文本中详细讲解此过程。 1. 创建目录 要在Java中创建一个新目录,可以使用如下代码: File dir = new File("path/to/directory"); boolean isCreated = dir.mk…

    Java 2023年5月20日
    00
  • SpringBoot3.0自定stater模块的操作流程(chatGPT提供的49种场景)

    Spring Boot 3.0 自定义 Starter 模块的操作流程 Spring Boot 3.0 是一个快速构建 Spring 应用程序的框架,它提供了许多便利的功能,例如自动配置、嵌入式服务器和健康检查等。在本文中,我们将详细讲解 Spring Boot 3.0 自定义 Starter 模块的操作流程。 什么是 Starter 模块 Starter …

    Java 2023年5月15日
    00
  • Tomcat服务器搭建教程

    Tomcat服务器搭建教程 安装JDK Tomcat服务器需要Java环境支持,因此需要先安装Java Development Kit (JDK)。 访问Oracle官方网站下载页面,选择合适的JDK版本下载。 安装JDK,设置环境变量。 下载Tomcat 访问Apache官网的下载页面,选择最新的稳定版本下载。 解压下载文件至目标文件夹。 配置Tomcat…

    Java 2023年5月19日
    00
  • Spring Security 核心过滤器链讲解

    Spring Security 是基于 Spring 框架的一个安全框架,可用于在 Web 应用程序中添加身份验证和授权的安全性。在 Spring Security 中,过滤器链起着至关重要的作用。本文将从以下几个方面详细讲解 Spring Security 核心过滤器链的完整攻略: Spring Security 核心过滤器链简介 Spring Secur…

    Java 2023年6月3日
    00
  • Netty结合Protobuf进行编解码的方法

    Netty结合Protobuf进行编解码的方法可以分为以下步骤: 添加依赖 为了使用Netty结合Protobuf进行编解码,需要添加以下两个依赖到项目的构建文件中: <!– 定义 protobuf 插件 –> <plugin> <groupId>org.xolstice.maven.plugins</group…

    Java 2023年5月20日
    00
  • JAVA创建和销毁对象的方法

    下面是关于JAVA创建和销毁对象的方法的详细攻略: 一、对象创建方法 对象的创建可以使用“new”关键字来实现。具体方法如下: 1.1 声明对象 首先需要声明一个类,并指定该类的数据类型。例如: public class Person { private String name; private int age; public Person(String n…

    Java 2023年5月26日
    00
  • Java 获取指定日期的实现方法总结

    Java 获取指定日期的实现方法总结 本文总结了在Java中获取指定日期的几种常见方法。 1. 通过日期字符串生成日期对象 在Java中,我们可以通过日期字符串生成日期对象,然后可以进行各种操作。下面是一个示例代码: import java.text.SimpleDateFormat; import java.util.Date; public class …

    Java 2023年5月20日
    00
  • jsp实现局部刷新页面、异步加载页面的方法

    让我来为您详细讲解一下“JSP实现局部刷新页面、异步加载页面的方法”的完整攻略。 前言 JSP(Java Server Pages)是一种基于Java技术的Web开发技术,它允许开发人员在HTML标签中包含Java代码,并通过编译器将其转换为Java Servlet。JSP通常与MVC(Model-View-Controller)设计模式一起使用,它允许开发…

    Java 2023年6月15日
    00
合作推广
合作推广
分享本页
返回顶部