iis服务器助手广告广告
返回顶部
首页 > 资讯 > 后端开发 > JAVA >Go面试题:锁的实现原理sync-mutex篇
  • 641
分享到

Go面试题:锁的实现原理sync-mutex篇

golangjava面试 2023-10-01 17:10:06 641人浏览 薄情痞子
摘要

在Go中,主要实现了两种锁:sync.Mutex(互斥锁) 以及 sync.RWMutex(读写锁)。 本篇主要给大家介绍sync.Mutex的使用和实现原理。 文章目录 为什么需要锁在Go中

Go中,主要实现了两种:sync.Mutex(互斥锁) 以及 sync.RWMutex(读写锁)。

本篇主要给大家介绍sync.Mutex的使用和实现原理。

文章目录

为什么需要锁

高并发下或多goroutine同时执行下,可能会同时读写同一块内存,比如如下场景:

var count intvar mu sync.Mutexfunc func1() {for i := 0; i < 1000; i++ {go func() {count = count + 1}()}time.Sleep(time.Second)fmt.Println(count)}

输出的值预期是1000,实际是 948,965等,多次运行结果不一致。
之所以出现这样的现象,是因为对于count=count+1来讲,每个goroutine执行步骤为:

  • 读取当前count值
  • count+1
  • 修改count值

当多个goroutine同时执行修改数值时,后面执行的goroutine会把前面goroutine对count的修改覆盖。

在Go中对于并发程序进行公共资源的访问的限制最常用的就是互斥锁(sync.mutex)的方式

sync.mutex的常用方法有两个:

  • Mutex.lock()用来获取锁
  • Mutex.Unlock()用于释放锁
    在 Lock 和 Unlock 方法之间的代码段称为资源的临界区,这一区间的代码是严格被锁保护的,是线程安全的,任何一个时间点最多只能有一个goroutine在执行。

基于此,上面的示例可以采用sync.mutex来改进:

var count intvar mutex sync.Mutexfunc func2() {for i := 0; i < 1000; i++ {go func() {mutex.Lock()count = count + 1mutex.Unlock()}()}time.Sleep(time.Second)fmt.Println(count)}

输出结果为1000。

当某一goroutine执行了mutex.lock()方法后,如果有其他的goroutine来执行上锁操作,会被阻塞,直到当前的goroutine执行mutex.unlock()方法释放锁后其他的goroutine才会继续抢锁执行。

实现原理

sync.Mutex的数据结构
Go中的sync.Mutex的结构体为:

type Mutex struct {state int32sema  uint32}

Sync.Mutex由两个字段构成,state用来表示当前互斥锁处于的状态,sema用于控制锁状态的信号量。相信各位道友读完这两个字段的描述后,好像懂了,又好像没懂。下面我们详细理解下这两个字段到底都作了哪些事。
互斥锁state主要记录了如下四种状态:

waiter_num: 记录了当前等待抢这个锁的goroutine数量
starving: 当前锁是否处于饥饿状态 (后文会详解锁的饥饿状态) 0: 正常状态 1: 饥饿状态
woken: 当前锁是否有goroutine已被唤醒。 0:没有goroutine被唤醒; 1: 有goroutine正在加锁过程
locked: 当前锁是否被goroutine持有。 0: 未被持有 1: 已被持有
sema信号量的作用
当持有锁的gorouine释放锁后,会释放sema信号量,这个信号量会唤醒之前抢锁阻塞的gorouine来获取锁。

锁的两种模式

互斥锁在设计上主要有两种模式: 正常模式和饥饿模式。

之所以引入了饥饿模式,是为了保证goroutine获取互斥锁的公平性。所谓公平性,其实就是多个goroutine在获取锁时,goroutine获取锁的顺序,和请求锁的顺序一致,则为公平。
正常模式下,所有阻塞在等待队列中的goroutine会按顺序进行锁获取,当唤醒一个等待队列中的goroutine时,此goroutine并不会直接获取到锁,而是会和新请求锁的goroutine竞争。 通常新请求锁的goroutine更容易获取锁,这是因为新请求锁的goroutine正在占用cpu片执行,大概率可以直接执行到获取到锁的逻辑。

饥饿模式下, 新请求锁的goroutine不会进行锁获取,而是加入到队列尾部阻塞等待获取锁。
饥饿模式的触发条件

  • 当一个goroutine等待锁的时间超过1ms时,互斥锁会切换到饥饿模式

饥饿模式的取消条件:

  • 当获取到锁的这个goroutine是等待锁队列中的最后一个goroutine,互斥锁会切换到正常模式
  • 当获取到锁的这个goroutine的等待时间在1ms之内,互斥锁会切换到正常模式

注意事项

  1. 在一个goroutine中执行Lock()加锁成功后,不要再重复进行加锁,否则会panic。
  2. 在Lock() 之前 执行Unlock()释放锁 会panic
  3. 对于同一把锁,可以在一个goroutine中执行Lock加锁成功后,可以在另外一个gorouine中执行Unlock释放锁。

来源地址:https://blog.csdn.net/m0_73728511/article/details/133011077

--结束END--

本文标题: Go面试题:锁的实现原理sync-mutex篇

本文链接: https://www.lsjlt.com/news/422347.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • Go面试题:锁的实现原理sync-mutex篇
    在Go中,主要实现了两种锁:sync.Mutex(互斥锁) 以及 sync.RWMutex(读写锁)。 本篇主要给大家介绍sync.Mutex的使用和实现原理。 文章目录 为什么需要锁在Go中...
    99+
    2023-10-01
    golang java 面试
  • 如何理解Go里面的互斥锁mutex
    如何理解Go里面的互斥锁mutex,相信很多没有经验的人对此束手无策,为此本文总结了问题出现的原因和解决方法,通过这篇文章希望你能解决这个问题。1. 锁的基础概念1.1 CAS与轮询1.1.1 cas实现锁 在锁的实现中现在越来越多的采用C...
    99+
    2023-06-19
  • Go语言底层原理互斥锁的实现原理
    目录Go 互斥锁的实现原理?概念使用场景底层实现结构操作加锁解锁Go 互斥锁正常模式和饥饿模式的区别?正常模式(非公平锁)饥饿模式(公平锁)Go 互斥锁允许自旋的条件?Go 互斥锁的...
    99+
    2024-04-02
  • 阿里面试MySQL死锁问题的处理
    目录1、什么是死锁2、InnoDB 锁类型2.1、间隙锁( gap lock ) 2.2、next-key lock2.3、意向锁( Intention lock )2.4...
    99+
    2024-04-02
  • 《面试专题-----经典高频面试题收集一》解锁 Java 面试的关键:深度解析常见高频经典面试题(第一篇)
    大家好,我是码农阿豪,一位热爱 Java 编程的程序员。今天我想和大家分享一些常见的 Java 面试题,通过收集解析这些问题,希望能够帮助大家更好地准备面试,突破技术瓶颈,把面试官按在地上摩擦 。 ...
    99+
    2024-01-21
    面试 java
  • Synchronized的底层实现原理(原理解析,面试必备)
    synchronized 一. synchronized解读 1.1 简单描述 synchronized关键字解决的是多个线程之间访问资源的同步性,synchronized 翻译为中文的意思是同步,也称之为同步锁。 synchronize...
    99+
    2023-08-19
    面试 java jvm
  • JavaScript面试Module Federation实现原理详解
    目录基本概念1、什么是 Module Federation?2、Module Federation核心概念3、使用案例4、插件配置工作原理1、使用MF后在构建上有什么不同?2、如何加...
    99+
    2024-04-02
  • Go语言sync包与锁实现限制线程对变量的访问
    目录为什么需要锁互斥锁 Mutex读写锁Go语言中 sync 包里提供了互斥锁 Mutex 和读写锁 RWMutex 用于处理并发过程中可能出现同时两个或多个协程(或线程)读或写同一...
    99+
    2023-05-15
    Go语言 sync包 Go语言
  • 如何理解golang里面的读写锁实现与核心原理
    如何理解golang里面的读写锁实现与核心原理,很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。基础筑基读写锁的特点读写锁区别与互斥锁的主要区别就是读锁之间是共享的...
    99+
    2023-06-19
  • redis分布式锁的实现原理
    小编给大家分享一下redis分布式锁的实现原理,希望大家阅读完这篇文章后大所收获,下面让我们一起去探讨吧!分布式锁其实可以理解为:控制分布式系统有序的去对共享资源进行操作,通过互斥来保持一致性。举个不太恰当...
    99+
    2024-04-02
  • golang锁的实现原理是什么
    golang锁的实现原理是通过互斥锁和读写锁来保护共享资源的访问。互斥锁是一种基本的锁机制,用于保护共享资源,使用一个标志位来表示资源是否被占用,当一个goroutine获取到互斥锁后,其他goroutine就会被阻塞,直到该gorouti...
    99+
    2023-12-12
    Golang
  • Go defer的实现原理剖析
    本篇内容介绍了“Go defer的实现原理剖析”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!1. 前言de...
    99+
    2024-04-02
  • 怎么使用Go语言sync包与锁实现限制线程对变量的访问
    本篇内容主要讲解“怎么使用Go语言sync包与锁实现限制线程对变量的访问”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“怎么使用Go语言sync包与锁实现限制线程对变量的访问”吧!Go语言中 sy...
    99+
    2023-07-06
  • go 原子操作的方式及实现原理全面深入解析
    目录什么是原子操作?原子操作的使用场景是什么?原子操作是怎么实现的?x86 LOCK 的时候发生了什么原子操作有什么特征?go 里面有哪些原子操作?增减(Add)比较并交换(Comp...
    99+
    2023-05-16
    go 原子操作方式原理 go 原子操作
  • Java面试题之HashMap 的 hash 方法原理是什么
    Warning:这是《Java 程序员进阶之路》专栏的第 55 篇。 回来后小二找到了我,于是我就写下了这篇文章丢给他,并严厉地告诉他:再搞不懂就别来找我。听到这句话,心头一阵酸,小...
    99+
    2024-04-02
  • Java中锁的实现原理和实例用法
    这篇文章主要介绍“Java中锁的实现原理和实例用法”,在日常操作中,相信很多人在Java中锁的实现原理和实例用法问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”Java中锁的实现原理和实例用法”的疑惑有所帮助!...
    99+
    2023-06-16
  • Golang实现文件锁的原理及应用
    Golang实现文件锁的原理及应用 在操作系统中,文件锁是一种用于保护文件或资源不被多个进程同时访问或修改的机制。在Golang中,通过使用sync包提供的Mutex锁可以实现对内存中...
    99+
    2024-02-29
    应用 golang 文件锁
  • mysql行级锁的实现原理是什么
    MySQL行级锁的实现原理是通过两种方式来实现的:锁的粒度和锁的类型。 锁的粒度: MySQL的行级锁是在InnoDB存储引擎中...
    99+
    2024-04-09
    mysql
  • 深入剖析OpenMP锁的原理与实现
    目录前言深入分析 omp_lock_tomp_lock_t 源码分析深入分析 omp_nest_lock_tomp_nest_lock_t 源码分析源代码函数名称不同的原因揭秘总结前...
    99+
    2023-01-28
    OpenMP锁原理 OpenMP锁实现 OpenMP锁
  • Linux互斥锁的实现原理是什么
    本篇内容主要讲解“Linux互斥锁的实现原理是什么”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“Linux互斥锁的实现原理是什么”吧!互斥锁(Mutex)是在原子操作API的基础上实现的信号量行...
    99+
    2023-06-28
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作