首页 > 其他分享 >多线程的使用-->2

多线程的使用-->2

时间:2024-08-28 08:54:50浏览次数:8  
标签:状态 同步 变量 -- lock 对象 线程 使用 多线程

1.线程同步

当多线程执行,对于一个共享变量进行操作时,会产生一些安全问题,称为同步问题。

线程同步就是在多线程访问共享变量时,通过一定的机制,使得线程可以按照一定的顺序,每次只能有一个线程访问共享变量。

1.1解决线程同步

给程序枷锁     两种:

①.悲观锁:必须要上锁,有具体的上锁操作,悲观锁有两种,使用synchronized关键字,使用Lock对象

②.乐观锁:不是真正意义上的锁,没有具体的锁操作,但有一个数据状态。每次操作数据前,会获得数据状态。在操作数据时,如果发现状态发生了变化,基于新状态重新操作 ​ JDK针对于数字计算,提供了原子类,底层使用的是CAS + 自旋机制

( synchronized )锁的使用:该关键字可以给方法上锁,也可以给代码段上锁

  • 当线程调用同步方法或同步代码段时,就会获得一个对象锁

    每一个对象创建时,都会有一个对象锁,本质是一个监视器Mointer

  • 当synchronized关键字修饰的是方法时,调用该同步方法获得的是该方法所属对象的对象锁

    而不是调用这个方法的线程对象的对象锁

    当线程争抢对象锁时,如果对象所以被占用,线程将处于等待状态

    当另一个线程执行完毕,释放了占有的锁, 这些等待的线程才能继续执行。

  • 线程进入等待状态,本质就是加入了一个同步等待队列(是系统级别的)

方法

同步代码段:同步代码段所需要的锁,是通过传参指定的。只要保证传递对象是唯一的即可。

Lock锁的使用:Lock本身是一个接口,我们实际应用时使用其对应的子类ReentrantLock

Lock的使用过程

  1. 创建锁对象。 如果多个线程需要争抢一把锁,就创建一个锁对象。 需要多个锁,就创建多个锁对象

  2. 调用lock对象的lock()尝试争抢锁。 如果抢不到锁,线程进入等待状态。

    有一个从在方法tryLock(10,TimeUnit.SECONDS)尝试在指定的时间内获得锁。返回boolean

  3. 调用lock对象的unlock(),释放锁。 其他等待锁的线程才能继续争抢。

在使用lock锁,建议将获得锁的代码写在try中,将释放锁的代码写在finally中

确保无论操作是否成功还是是否,都能释放锁。

Lock锁的底层机制

底层使用的是CAS + AQS

  1. 在lock底层有一个计数器,记录锁被获取的状态,起初为0 , 当被抢占的时候变为1

    也就是说,当我们调用lock.lock()方法,就是将状态从0改为1的过程

    当我们调用lock,unlock()方法时,就是将状态从1改为0的过程

    当我们调用lock.lock方法时,如果发现状态是1,表示锁被占用,当前线程进入等待状态

  2. 当多个线程同时访问lock.lock()方法时,就想将状态从0改为1

    每个线程都尝试着将状态从0改为1. 假设a线程最先完成状态改变,a线程获得了锁

    此时b线程也尝试将0改为1,先获得原始值0,将0改为1,再将改好的1替换原始值0(赋值)

    在替换前,会拿着之前的原始值与现在变量里的值进行比较,看看是否发生了变化

    如果没有变化,说明这个过程中没有其他线程访问资源,将其改为1获得锁。

    如结发生了变化,说明这个过程中被其他线程捷足先登了,其他的线程获得锁,当前线程等待

    我们称这个过程为 CAS (compare and set)

  3. 当一个线程获得锁时,发现锁已经被占用了,当前这个线程就会处于等待状态

    实际上,并不是线程对象有一个状态码,改为等待状态的值。

    实际上是将需要等待的线程,存入了一个集合,并使其进入最终等待状态(jvm级别的等待状态)

    当最开始线程执行完毕释放锁后,就会从这个集合中取出最开始的那个线程继续执行

    这个集合我们就称为 AQS (抽象的)队列同步器

乐观锁的使用:乐观锁不是一种真正存在的锁,而是一种机制。  底层使用的是 CAS + 自旋 应用组合

  • 乐观锁的使用更具有局限性, 适用于数字变量的计算,一般多是 ++ 和 --

  • JDK中提供了一个原子类 AtomicIntger,该类对象中提供了++和--的计算方法

    当通过该类对象提供的++和--的方法计算时,可以确保线程同步。

AtomicInteger的常用方法

CAS特点是,在set设置新值之前,先用原始值与当前变量中的值做比较,相等说明这个过程中没有其他线程操作变量,也就相当于当前线程占有变量。不相等说明这个过程中有其他线程操作变量,也就是这个变量其他线程占有,我需要重新获得。

ABA问题:在比较时原始值与当前变量中的值相等,不能说明这个过程中变量没有被其他线程操作,因为有可能另一个线程将变量中的值,从A改成了B又改回成了A。

解决ABA:可以为数据增加一个版本号,只要改变过,版本号就+1

JDK提供了一个可以解决ABA问题的原子类

标签:状态,同步,变量,--,lock,对象,线程,使用,多线程
From: https://blog.csdn.net/lzp122390/article/details/141610564

相关文章

  • 巴特沃斯LPF设计(硬件电路实现)
    高阶(2n)VSVC单位增益巴特沃斯低通滤波器设计,可分解为n个二阶低通,通过对这多个二阶低通的组合优化,可提高滤波器的低通特性和稳定性。串联的传递函数是各个二阶滤波器传递函数的乘积:\({{\rm{H}}_{2n}}(s)=\prod\nolimits_{i-1}^n{{H_2}^{(i)}(s)}\);二阶压控电压源低通滤......
  • 领域驱动模型设计与微服务架构落地(四)之DDD分层架构设计
    那么聊完领域模型之后,其实我们会发现,接下来,很多的程序员可能就会直接上代码,因为很多的程序员觉得这个你的战略设计跟我们落地的代码没有关系。哪怕你可能说得天花乱坠,可是做为底层的开发人员,我只关心手头上的功能有没有实现,实现完成之后有没有BUG。那么我们该如何对于我们的系......
  • 推荐一款开源一站式SQL审核查询平台!功能强大、安全可靠!
    1、前言在当今这个数据驱动的时代,数据库作为企业核心信息资产的载体,其重要性不言而喻。随着企业业务规模的不断扩大,数据库的数量和种类也日益增多,这对数据库的管理与运维工作提出了前所未有的挑战。在这样的背景下,一款高效、易用的数据库管理工具显得尤为重要。Archery,作为一款开......
  • 考研系列-408真题数据结构篇(10-17)
    写在前面此文章是本人在备考过程中408真题数据结构部分(2010年-2017年)的易错题及相应的知识点整理,后期复习也尝尝用到,对于知识提炼归纳理解起到了很大的作用,分享出来希望帮助到大家~#2010年1.散列表处理冲突的方法......
  • Python数据采集与网络爬虫技术实训室解决方案
    在大数据与人工智能时代,数据采集与分析已成为企业决策、市场洞察、产品创新等领域不可或缺的一环。而Python,作为一门高效、易学的编程语言,凭借其强大的库支持和广泛的应用场景,在数据采集与网络爬虫领域展现出了非凡的潜力。唯众特此推出《Python数据采集与网络爬虫技术实训......
  • 南沙C++陈老师讲题:1078:求分数序列和
    ​【题目描述】【输入】输入有一行,包含一个正整数n(n≤30)n(n≤30)。【输出】输出有一行,包含一个浮点数,表示分数序列前nn项的和,精确到小数点后44位。【输入样例】2【输出样例】3.5000#include<iostream>#include<stdio.h>usingnamespacestd;intmain()......
  • STL所有常用算法(全网最详细,一文全掌握,建议收藏)
    目录1.分类和介绍2.遍历算法2.1for_each算法(遍历执行)2.2transform算法(搬运)3.查找算法3.1find算法(具体查找)3.2find_if算法(条件查找)3.3 adjacent_find(查找相邻重复元素)3.4 binary_search(二分查找有序序列中元素是否存在)3.5 count(统计元素出现次数)3.6 coun......
  • 程序控制流程面试题
    一.while和do…while的区别?使用while循环,当你需要在条件满足时执行循环,但不希望在条件一开始就不满足的情况下执行任何代码。使用do...while循环,当你需要确保循环体至少执行一次,然后根据条件决定是否继续执行。二.循环中,break的作用是什么?continue的作用是什么?break......
  • 计算机网络技术专业SDN(软件定义网络)实训室解决方案
    一、前言随着信息技术的飞速发展,网络架构正经历着前所未有的变革,其中软件定义网络(SDN,Software-DefinedNetworking)作为未来网络的核心技术之一,正逐步成为计算机网络技术专业教学与科研的重要方向。唯众,作为深耕职业教育领域的领先品牌,特推出针对计算机网络技术专业的SDN......
  • 用例基础知识
    •动态测试(dynamictesting):通过运行软件的组件或系统来测试软件•静态测试(statictesting):对组件的规格说明书进行评审,对静态代码进行走查=》看需求文档就属于静态测试•正式评审(formalreview):对评审过程及需求文档的一种特定评审交叉评审:测试组内测试人员互相评审对方用例......