【Java并发入门】03 互斥锁(上):解决原子性问题

news2024/11/16 4:27:38

原子性问题的源头是线程切换

Q:如果禁用 CPU 线程切换是不是就解决这个问题了?
A:单核 CPU 可行,但到了多核 CPU 的时候,有可能是不同的核在处理同一个变量,即便不切换线程,也有问题。

所以,解决原子性的关键是「同一时刻只有一个线程处理该变量,也被称为互斥」。

如何做到呢?用「锁」。

一、锁模型

一)简易锁模型

一般看到的锁模型长下面这样。

但对于这个模型,会有几个疑问:

  • 锁的是什么?
  • 临界区的这一堆代码相关的都被锁了?
  • 保护的又是什么?

image.png

二)改进后的锁模型

用下面这个模型来解释就解答了上面几个问题:

  • 要保护的是临界区中的资源 R
  • 因此要为 R 创建一个对应的锁 LR
  • 需要处理资源 R 的时候先加锁,处理完之后解锁

image.png

要注意的是:

  • 一个资源必须和锁对应,不能用 A 锁去锁 B 资源

二、Java 提供的锁技术

Java 提供了多种技术,这里仅谈及 Synchronized

Synchronized 关键字

Java 语言提供的 synchronized 关键字,就是锁的一种实现。synchronized 关键字可以用来修饰方法,也可以用来修饰代码块。

class X {
  // 修饰非静态方法
  synchronized void foo() {
    // 临界区
  }
  // 修饰静态方法
  synchronized static void bar() {
    // 临界区
  }
  // 修饰代码块
  Object obj = new Object()void baz() {
    synchronized(obj) {
      // 临界区
    }
  }
}  

Q:synchronized 没看到 lock 和 unlock?
A:在编译的时候会做转换,synchronized起始的地方加锁,结束的地方解锁。

Q:那么 synchronized 锁的是什么呢?
A:当修饰静态方法时,锁定的是当前类的 Class 对象,在上面的例子中就是 Class X;
当修饰非静态方法时,锁定的是当前实例对象 this。
当修饰代码块时,括号中写的是啥就锁啥。

(可能不准确)
Class 对象是用来保存类信息的,可以理解为元数据?
实例对象则是每一个 new 出来的特殊的个体

Synchronized 实例

public class SynchronizedTT  {
    private int value = 0;

    //public void printValue() {
    public synchronized void printValue() {
        System.out.println(this.value);
    }

    public synchronized void addValue() throws InterruptedException {
        Thread.sleep(1000);
        this.value += 1;
    }
}

// 开两个线程,一个先调用 addValue(),另一个后调用 printValue()

💡思考:如果 printValue() 不添加 synchronized 关键字,会造成什么样的结果?
A:有可能会先执行了 addValue 在执行 print 但得到的却是增加之前的数值。

三、锁和受保护资源的关系

要点:

  • 一把锁可以保护多个资源
  • 但是一个资源只能用一把锁保护
  • 受保护资源和锁之间的关联关系是 N:1 的关系

💡思考:如果用多把锁锁同一个资源会出现什么情况?

下面例子:
synchronized 是不同的锁,就和没锁一样。

public class SynchronizedTT  {
    private static int value = 0;

    public synchronized void printValue() {
        System.out.println(value);
    }

    public synchronized static void addValue() throws InterruptedException {
        Thread.sleep(1000);
        value += 1;
    }
}

image.png

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

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

相关文章

C++代码基本内存操作及原理

文章目录前言操作系统内存地址空间基本数据类型sizeof运算符指针运算内存分配与回收堆与栈malloc/new与free/delete基本类型的指针操作类定义中的内存使用前言 ​ C凭借其指针变量可以直接操作内存而得到了非常高的效率和程序性能,在一种编程语言里独树一帜。当然&…

网络变压器工厂:了解POE POE+ 网络变压器(网络隔离滤波器)

Hqst盈盛(华强盛)电子导读:这一节给大家分享:POE POE POE 网络变压器(网络滤波器,网络隔离变压器)的相关知识--poe poe 与POE简介及相关标准; 一、网络变压器 POE、 POE 与POE简介 POE 是Power …

Day17-购物车页面-收货地址-把address信息存储到vuex中

1.将address信息存储到vuex中: 我的操作: 1》在 store 目录中,创建用户相关的 vuex 模块,命名为 user.js: ①:新建user.js文件 ②:为user.js编写内容 2》在 store/store.js 模块中&#xff0c…

typora安装和配置PicGo图床

typora安装和配置PicGo图床typora安装和配置PicGo图床typora安装安装picgo图床配置picgo图床图床服务器picgo配置七牛云typora安装和配置PicGo图床 typora安装 windows安装typora 参考:https://www.bilibili.com/read/cv19476097/ m1 mac安装typora比较简单&…

数据结构-栈ArrayDeque的实现

优雅,实在是太优雅了 能把复杂的东西简单化就是功底。 我为何有如此感慨,了解ArrayDeque的实现你就知道,今天我们要讲的是以栈为思想而实现的ArrayDeque,我们都知道栈是先进后出,和队列相反,如下图&#x…

二叉树的中序遍历三种解法(递归+迭代+线索化)

文章目录递归迭代线索二叉树解法传送门: 添加链接描述 给你一颗二叉树,让你实现中序的遍历 递归 递归没什么好说的,直接无脑递归即可,时间复杂度:O(n),空间复杂度:O&am…

搭建环境AI画图stable-diffusion

目录简介环境准备安装conda(方式1)安装conda(方式2,推荐)验证conda安装成功安装stable-diffusion的环境简介 本文旨在记录过程,偶然看见一个AI画图的,体验看看。 stable-diffusion是一个输入简单图片,输出…

【Java难点攻克】「Guava RateLimiter」针对于限流器的入门到实战和源码原理分析

限流器的思路和算法 如果让你来造一个限流器,有啥想法? 漏桶算法 用一个固定大小的队列。比如设置限流为5qps,1s可以接受5个请求;那我们就造一个大小为5的队列,如果队列为满了,就拒绝请求;如…

JRebelXRebel的配置和使用(进阶篇)

JRebel&XRebel的配置和使用嘚吧嘚设置JRebel快捷键XRebel使用嘚吧嘚 之前简单介绍了JRebel&XRebel的安装和使用,不了解的朋友可以补补课😆。 JRebel&XRebel这款插件不仅仅可以用来热部署,所以继续分享一下这款插件的相关使用&a…

12月2日(第四天)

使用myabtis自动生成的时候&#xff0c;发现xml文件只会merge不会覆盖&#xff0c;这时候需要使用插件&#xff1a; <plugin type"org.mybatis.generator.plugins.UnmergeableXmlMappersPlugin" />MyBatis Generator配置文件context元素的defaultModelType属性…

封装window10-21H1踩的坑,无法分析或处理pass[specialize]应答文件

最近在研究封装镜像&#xff0c;无奈公司不给用win11&#xff0c;只能封装win10 2022年全新Windows11系统封装图文教程&#xff08;一&#xff09;定制母盘 - 小鱼儿yr系统 (yrxitong.com) 坑1&#xff0c;封装好出现无法分析或处理pass[specialize]应答文件 解决办法&#x…

Java基础:String类、static关键字、Arrays类、Math类

第一章 String类 1.1 String类概述 概述 java.lang.String类代表字符串。Java程序中所有的字符串文字&#xff08;例如"abc"&#xff09;都可以被看作是实现此类的实例。 类String中包括用于检查各个字符串的方法&#xff0c;比如用于比较字符串&#xff0c;搜索…

[附源码]计算机毕业设计JAVA新冠疫苗线上预约系统

[附源码]计算机毕业设计JAVA新冠疫苗线上预约系统 项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM my…

Web3.0 DApp(去中心化应用程序)设计架构

先来回顾下 Web2.0 应用程序架构&#xff0c;一图胜千言&#xff1a; 图示是对大多数 Web 2.0 应用程序如何工作的一个很好的抽象总结。以一个博客平台为例&#xff1a; 首先&#xff0c;必须有一个地方来存储基本数据&#xff0c;也就是数据库&#xff1b; 其次&#xff0c;…

快速串联 RNN / LSTM / Attention / transformer / BERT / GPT(未完待续)

参考&#xff1a; 李宏毅2021/2022春机器学习课程王树森 RNN & Transformer 教程 文章目录0. 背景&#xff1a;序列数据及相关任务1. 早期序列模型1.1 循环神经网络 RNN1.2 长短期记忆网络 LSTM1.3 改善 RNN/LSTM 的三个技巧1.3.1 通过堆叠扩展为深度模型1.3.2 使用双向模…

使用学校的服务器跑深度学习

&#x1f31e;欢迎来到深度学习的世界 &#x1f308;博客主页&#xff1a;卿云阁 &#x1f48c;欢迎关注&#x1f389;点赞&#x1f44d;收藏⭐️留言&#x1f4dd; &#x1f31f;本文由卿云阁原创&#xff01; &#x1f320;本阶段属于练气阶段&#xff0c;希望各位仙友顺利完…

原型工具与代码实现的差距及改进设想

背景 最近经常根据墨刀设计的原型开发微信小程序页面&#xff0c;使用的多了总感觉原型只能参考&#xff0c;原型跟代码实现总差一小步。原型中提供的CSS并不能直接复制到代码中&#xff0c;导致编码人员复刻原型设计时总有差距。本文先列举出一些原型和实现的差距&#xff0c;…

RS232/RS485信号转12路模拟信号 隔离D/A转换器YL34

特点&#xff1a; ● RS-485/232接口&#xff0c;隔离转换成12路标准模拟信号输出 ● 可选型输出4-20mA或0-10V控制其他设备 ● 模拟信号输出精度优于 0.2% ● 可以程控校准模块输出精度 ● 信号输出 / 通讯接口之间隔离耐压3000VDC ● 宽电源供电范围&#xff1a;10 ~ 3…

信息收集的工具简介和常见操作

目录 前言 域名信息 工具 子域名信息 工具 域名DNS解析信息 工具 ip信息 工具 CDN绕过 方法 工具 端口服务信息 常见端口总结 基本概念 扫描工具 指纹识别 识别对象 cms指纹识别 识别思路 工具 其他工具 cdn识别 常用工具 waf识别 触发 工具 Google…

营业利润里首次突破两位数,瑞幸能否延续神话?

近期&#xff0c;瑞幸咖啡公布了Q3财报&#xff0c;三季度继续延续了上半年良好的增长势能。总净收入39亿元&#xff0c;同比增长65.7%&#xff0c;营业利润率首次突破双位数达到了15%。 门店数量增长&#xff1a;Q3新增651家&#xff0c;达到7846家门店。从开店节奏看&#…