Java多线程中的互斥锁解析

 更新时间:2023年09月15日 11:06:07   作者:伊颦伊笑  
这篇文章主要介绍了Java多线程中的互斥锁解析,Java语言中,引入了对象互斥锁的概念,来保证共享数据操作的完整性,每个对象都对应于一个可称为互斥锁的标记,这个标记用来保证在任一时刻,只能有一个线程访问该对象,需要的朋友可以参考下

基本介绍

  1. Java语言中,引入了对象互斥锁的概念,来保证共享数据操作的完整性。
  2. 每个对象都对应于一个可称为 “ 互斥锁 ” 的标记,这个标记用来保证在任一时刻,只能有一个线程访问该对象。
  3. 关键字 synchronized 来与对象的互斥锁联系。当某个对象用 synchronized 修饰时,表明该对象在任一时刻只能由一个线程访问
  4. 同步的局限性:导致程序的执行效率要降低
  5. 同步方法(非静态的)的锁可以是this,也可以是其他对象(要求是同一个对象)
  6. 同步方法(静态的)的锁为当前类本身。

把 synchronized 写在代码块上

package thread_;
/**
 * @Author: Gin
 * @Description:
 * @Modified By: Gin
 * @Date: Created in 16:37 2021/9/27
 */
public class Thread11 {
    public static void main(String[] args) {
        SellThread04 sellThread04 = new SellThread04();
        new Thread(sellThread04).start();
        new Thread(sellThread04).start();
        new Thread(sellThread04).start();
    }
}
class SellThread04 implements Runnable{
    private int ticketsNum = 100;
    private boolean flag = true;
    @Override
    public void run() {
        while (flag) {
            sell();
        }
    }
    /*
        1. public synchronized void sell(){} 就是一个同步方法
        2. 这时“锁”在 this 对象上
        3. 也可以在代码块上写 synchronized,同步代码块,互斥锁还是在 this 对象上
           如下:
     */
    public /* synchronized */ void sell(){
        synchronized (this) {
            if(ticketsNum <= 0){
                System.out.println("售票结束...");
                flag = false;
                return;
            }
            try {
                Thread.sleep(50);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println("窗口 " + Thread.currentThread().getName() + " 售票一张, 剩余票数 " + (--ticketsNum));
        }
    }
}

测试操作同一个对象、静态方法的锁的添加

package thread_;
/**
 * @Author: Gin
 * @Description:
 * @Modified By: Gin
 * @Date: Created in 16:37 2021/9/27
 */
public class Thread11 {
    public static void main(String[] args) {
        SellThread04 sellThread04 = new SellThread04();
        new Thread(sellThread04).start();
        new Thread(sellThread04).start();
        new Thread(sellThread04).start();
    }
}
class SellThread04 implements Runnable{
    private int ticketsNum = 100;
    private boolean flag = true;
    // 同步方法(非静态的)的锁可以是this,也可以是其他对象(要求是同一个对象)
    // new 一个 Object 对象,测试操作同一个对象
    Object object = new Object();
    // 同步方法(静态的)的锁为当前类本身。
    public synchronized static void m1(){
        System.out.println("m1");
    }
    // 在静态方法中实现一个同步代码块
    public static void m2(){
        synchronized (SellThread04.class) {
            System.out.println("m2");
        }
    }
    @Override
    public void run() {
        while (flag) {
            sell();
        }
    }
    /*
        1. public synchronized void sell(){} 就是一个同步方法
        2. 这时“锁”在 this 对象上
        3. 也可以在代码块上写 synchronized,同步代码块,互斥锁还是在 this 对象上
           如下:
     */
    public /* synchronized */ void sell(){
        synchronized ( /*this*/ object ) { // 测试操作同一个对象
            if(ticketsNum <= 0){
                System.out.println("售票结束...");
                flag = false;
                return;
            }
            try {
                Thread.sleep(50);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println("窗口 " + Thread.currentThread().getName() + " 售票一张, 剩余票数 " + (--ticketsNum));
        }
    }
}

细节

同步方法如果没有使用 static 修饰:默认锁对象为 this如果方法使用 static 修饰,默认锁对象:当前类.class

到此这篇关于Java多线程中的互斥锁解析的文章就介绍到这了,更多相关Java互斥锁内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Nacos服务多级存储模型使用及说明

    Nacos服务多级存储模型使用及说明

    文章介绍了服务分级存储模型,通过Nacos将同一机房内的实例划分为一个集群,微服务互相访问时应优先访问同集群实例,以提高访问速度,通过配置application.yml文件,可以实现集群的创建和管理
    2026-02-02
  • j2ee mybatis注解@Data,@TableName,@TableField使用方式

    j2ee mybatis注解@Data,@TableName,@TableField使用方式

    这篇文章主要介绍了j2ee mybatis注解@Data,@TableName,@TableField使用方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-04-04
  • Flink实现往Kafka中多个topic发送消息

    Flink实现往Kafka中多个topic发送消息

    文章介绍了使用Flink 1.13.2 和 Kafka 2.6.2 从Kafka读取数据,并根据逻辑将数据分配到不同的topic,提到了需要重写FlinkKafka的Key序列化器,并加入自定义逻辑以发送消息到指定的topic,文中还包括了配置Kafka信息和如何连接FlinkKafka的步骤
    2025-10-10
  • 详解Java如何有效避免空指针

    详解Java如何有效避免空指针

    空指针,也就是NullPointerException 简称NPE的,怕一下子写出NPE,部分的伙伴看不懂,索性就改成了空指针,在实际的开发中,我们最讨厌的就是遇到空指针了,业务跑着跑着发现了空指针,所以本文详细介绍了Java如何有效的避免空指针,需要的朋友可以参考下
    2023-12-12
  • java递归法求字符串逆序

    java递归法求字符串逆序

    这篇文章主要介绍了java递归法求字符串逆序,涉及java递归调用的相关操作技巧,需要的朋友可以参考下
    2015-05-05
  • 纯Java手写TopoJSON生成器的实现

    纯Java手写TopoJSON生成器的实现

    本文实现了纯 Java、零依赖、可直接运行的 TopoJSON 生成器工具类,相比简易实现,更贴合生产环境需求,文中通过示例代码介绍的非常详细,需要的朋友们下面随着小编来一起学习学习吧
    2026-03-03
  • Java中的魔法值解决

    Java中的魔法值解决

    这篇文章主要介绍了Java中的魔法值解决,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-01-01
  • Eclipse中改变默认的workspace的方法及说明详解

    Eclipse中改变默认的workspace的方法及说明详解

    eclipse中改变默然的workspace的方法有哪几种呢?接下来脚本之家小编给大家介绍Eclipse中改变默认的workspace的方法及说明,对eclipse改变workspace相关知识感兴趣的朋友一起学习吧
    2016-04-04
  • 为什么Java项目中别用!=null做判空

    为什么Java项目中别用!=null做判空

    本文主要介绍了为什么Java项目中别用!=null做判空,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2023-04-04
  • JavaCV 拉流存储到本地示例解析

    JavaCV 拉流存储到本地示例解析

    这篇文章主要介绍了JavaCV 拉流存储到本地示例解析,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-08-08

最新评论