当前位置: 首页 > news >正文

Golang 基于共享变量的并发锁

一、互斥锁

先看一个并发情况,同时操作一个全局变量,如果没有锁会怎么样

假设有1000个goroutines并发进行银行余额的扣除,每次都扣除10元,起始的总余额是10000,理论上并发执行完应该是0对不对,但实际却不是

import ("fmt""sync"
)var balance uint = 10000func withdraw(amount uint) {balance = balance - amountfmt.Println("剩余存款:", balance)defer wg.Done()
}func getBalance() uint {return balance
}func main() {for i := 1; i <= 1000; i++ {wg.Add(1)go withdraw(10)}wg.Wait()fmt.Println(getBalance())
}

得到的结果如下:

这时候就需要引入一个锁来保护balance全局变量,在并发goroutines执行的情况下,防止其他goroutines获取到balance变量进行操作(其他goroutines会处于等待锁的状态)

import ("fmt""sync"
)var balance uint = 10000
var mu sync.Mutex
var wg sync.WaitGroupfunc withdraw(amount uint) {//如果其它的goroutine已经获得了这个锁的话,这个操作会被阻塞直到其它goroutine调用了Unlock使该锁变回可用状态。mutex会保护共享变量。mu.Lock()                       ******************* 增加锁 **********************balance = balance - amountfmt.Println("剩余存款:", balance)mu.Unlock()                     ******************* 释放锁 **********************defer wg.Done()
}func getBalance() uint {return balance
}func main() {for i := 1; i <= 1000; i++ {wg.Add(1)go withdraw(10)}wg.Wait()fmt.Println(getBalance())
}

得到的结果如下:

二、读写锁

RWMutex,即读写互斥锁,适用于读操作远远多于写操作的场景,当多个goroutine需要频繁地读取某个共享资源,而写入操作相对较少时,使用RWMutex可以提高并发性能。

func getBalance() uint {rwMu.RLock()               *********  加锁读取 ********defer rwMu.RUnlock()       ********* 返回释放锁 ********return balance
}

原理:RWMutex允许多个goroutine同时获取读锁(RLock),进行并发读操作,而写锁(Lock)则是互斥的,同一时间只允许一个goroutine进行写操作。当一个goroutine获取读锁时,其他goroutine也可以继续获取读锁来读取数据,而不需要等待。只有当有goroutine尝试获取写锁时,读锁才会被阻塞,这样可以有效地提高并发读取的效率。

sync.RWMutex锁的设计就是为了优化读操作频繁的场景。它能够区分读锁(RLock)和写锁(Lock)

读锁(RLock):
当一个goroutine需要读取共享资源时,它会尝试获取读锁。如果当前没有其他goroutine持有写锁,那么它可以成功获取读锁,并且可以并发地读取数据。如果有其他goroutine已经持有读锁,新的读锁请求也会被允许,从而允许多个goroutine同时读取。

写锁(Lock):
当一个goroutine需要写入共享资源时,它会尝试获取写锁。在写锁被获取之前,所有的读锁和写锁请求都会被阻塞。这意味着,一旦有goroutine开始写操作,其他想要读取或写入的goroutine都必须等待,直到写操作完成并且写锁被释放。

锁的释放:
当一个goroutine完成读取或写入操作后,它会释放相应的锁。如果是读操作完成,它会释放读锁,这样其他正在等待的goroutine就可以获取读锁并开始读取。如果是写操作完成,它会释放写锁,这样其他正在等待的读锁或写锁请求就可以继续进行。

RWMutex的这种设计使得在读操作远多于写操作的情况下,可以提高程序的并发性能。因为多个goroutine可以同时读取,而不需要等待写操作完成,这样就减少了锁竞争,提高了整体的吞吐量。然而,需要注意的是,RWMutex并不是在所有情况下都能提高性能。如果写操作非常频繁,或者读写操作几乎同等频繁,使用RWMutex可能会导致性能下降,因为写操作会阻塞所有读锁和写锁的请求。在这种情况下,使用Mutex可能会更加合适。

相关文章:

Golang 基于共享变量的并发锁

一、互斥锁 先看一个并发情况&#xff0c;同时操作一个全局变量&#xff0c;如果没有锁会怎么样 假设有1000个goroutines并发进行银行余额的扣除&#xff0c;每次都扣除10元&#xff0c;起始的总余额是10000&#xff0c;理论上并发执行完应该是0对不对&#xff0c;但实际却不…...

探索分布式技术--------------注册中心zookeeper

目录 一、ZooKeeper是什么 二、ZooKeeper的工作机制 三、ZooKeeper特点 四、ZooKeeper数据结构 五、ZooKeeper应用场景 5.1统一命名服务 5.2统一配置管理 5.3统一集群管理 5.4服务器动态上下线 5.5软负载均衡 六、ZooKeeper的选举机制 6.1第一次启动选举机制 6.2非…...

剑指offer之牛客与力扣——前者分类题单中的题目在后者的链接

搜索 [4.12完成] JZ1 LCR 172. 统计目标成绩的出现次数 JZ3 153. 寻找旋转排序数组中的最小值 JZ4 LCR 014. 字符串的排列 JZ5 LCR 163. 找到第 k 位数字 400 动态规划 [4.15完成] JZ2 LCR 161. 连续天数的最高销售额 53 JZ3 LCR 127. 跳跃训练 70 JZ4 LCR 126. 斐波那契…...

C# WinForm —— 05 控件简介

简介 窗体中用于输入或操作的对象&#xff0c;有自己的属性、方法、事件 属性&#xff1a;外观方法&#xff1a;功能事件&#xff1a;行为控制特征 可视化&#xff0c;与用户进行交互&#xff0c;属性&#xff0c;方法&#xff0c;事件&#xff0c;可供开发人员使用&#xff0…...

JavaEE实验三:3.5学生信息查询系统(动态Sql)

题目要求: 使用动态SQL进行条件查询、更新以及复杂查询操作。本实验要求利用本章所学知识完成一个学生信息系统&#xff0c;该系统要求实现3个以下功能: 1、多条件查询&#xff1a; 当用户输入的学生姓名不为空&#xff0c;则根据学生姓名进行学生信息的查询&#xff1b; 当用户…...

【爬虫开发】爬虫从0到1全知识md笔记第5篇:Selenium课程概要,selenium的其它使用方法【附代码文档】

爬虫开发从0到1全知识教程完整教程&#xff08;附代码资料&#xff09;主要内容讲述&#xff1a;爬虫课程概要&#xff0c;爬虫基础爬虫概述,,http协议复习。requests模块&#xff0c;requests模块1. requests模块介绍,2. response响应对象,3. requests模块发送请求,4. request…...

【我的代码生成器】React的FrmUser类源码

FrmUser 类的源码中&#xff1a;FrmUser btnSaveClick 等命名方式都是参考VB.Net的写法。 import React, { forwardRef, useImperativeHandle, useState, useEffect, } from "react"; import { makeStyles, TextField, Grid, Paper, Button, ButtonGroup, } from &q…...

Flutter 单例模式的多种实现方法与使用场景分析

单例模式是一种常用的设计模式&#xff0c;用于确保一个类只有一个实例&#xff0c;并提供一个全局访问点。在Flutter应用程序中&#xff0c;单例模式可以有效地管理全局状态、资源共享和对象的生命周期。本文将介绍Flutter中实现单例模式的多种方法&#xff0c;并分析它们的使…...

C语言洛谷题目分享(9)奇怪的电梯

目录 1.前言 2.题目&#xff1a;奇怪的电梯 1.题目描述 2.输入格式 3.输出格式 4.输入输出样例 5.说明 6.题解 3.小结 1.前言 哈喽大家好啊&#xff0c;前一段时间小编去备战蓝桥杯所以博客的更新就暂停了几天&#xff0c;今天继续为大家带来题解分享&#xff0c;希望大…...

vue 中使 date/time/datetime 类型的 input 支持 placeholder 方法

一般在开发时&#xff0c;设置了 date/time/datetime 等类型的 input 属性 placeholder 提示文本时&#xff0c; 发现实际展示中却并不生效&#xff0c;如图&#xff1a; 处理后效果如图&#xff1a; 处理逻辑 判断表单项未设置值时&#xff0c;则设置其伪类样式&#xff0c;文…...

书生·浦语大模型全链路开源体系-第3课

书生浦语大模型全链路开源体系-第3课 书生浦语大模型全链路开源体系-第3课相关资源RAG 概述在 InternLM Studio 上部署茴香豆技术助手环境配置配置基础环境下载基础文件下载安装茴香豆 使用茴香豆搭建 RAG 助手修改配置文件 创建知识库运行茴香豆知识助手 在茴香豆 Web 版中创建…...

Weblogic任意文件上传漏洞(CVE-2018-2894)漏洞复现(基于vulhub)

&#x1f36c; 博主介绍&#x1f468;‍&#x1f393; 博主介绍&#xff1a;大家好&#xff0c;我是 hacker-routing &#xff0c;很高兴认识大家~ ✨主攻领域&#xff1a;【渗透领域】【应急响应】 【Java、PHP】 【VulnHub靶场复现】【面试分析】 &#x1f389;点赞➕评论➕收…...

链表基础3——单链表的逆置

链表的定义 #include <stdio.h> #include <stdlib.h> typedef struct Node { int data; struct Node* next; } Node; Node* createNode(int data) { Node* newNode (Node*)malloc(sizeof(Node)); if (!newNode) { return NULL; } newNode->data …...

Fiddler:网络调试利器

目录 第1章:Fiddler简介和安装 1.1 Fiddler概述 1.2 Fiddler的安装步骤 步骤1:下载Fiddler 步骤2:运行安装程序 步骤3:启动Fiddler 1.3 配置Fiddler代理 配置操作系统代理 配置浏览器代理 Google Chrome Mozilla Firefox 第2章:Fiddler界面和基本操作 2.1 Fi…...

【笔记】mysql版本6以上时区问题

前言 最近在项目中发现数据库某个表的createTime字段的时间比中国时间少了13个小时&#xff0c;只是在数据库中查看显示时间不对&#xff0c;但是在页面&#xff0c;又是正常显示中国时区的时间。 排查 项目中数据库的驱动使用的是8.0.19&#xff0c;驱动类使用的是com.mysq…...

Scala实战:打印九九表

本次实战的目标是使用不同的方法实现打印九九表的功能。我们将通过四种不同的方法来实现这个目标&#xff0c;并在day02子包中创建相应的对象。 方法一&#xff1a;双重循环 我们将使用双重循环来实现九九表的打印。在NineNineTable01对象中&#xff0c;我们使用两个嵌套的fo…...

Excel文件解析

在此模块的学习中&#xff0c;我们需要一个新的开源类库---Apahche POI开源类库。这个类库的用途是&#xff1a;解析并生成Excel文件(Word、ppt)。Apahche POI基于DOM方式进行解析&#xff0c;将文件直接加载到内存&#xff0c;所以速度比较快&#xff0c;适合Excel文件数据量不…...

纯css实现switch开关

代码比较简单&#xff0c;有需要直接在下边粘贴使用吧~ html: <div class"switch-box"><input id"switch" type"checkbox"><label></label></div> css&#xff1a; .switch-box {position: relative;height: 25px…...

Unity3d 微信小游戏 AB资源问题

简介 最近在做微信小游戏&#xff0c;因为对unity比较熟悉&#xff0c;而且微信也支持了用unity3d直接导出到小游戏的工具&#xff0c;所以就记录下这期间遇到的问题 微信小游戏启动时间主要受以下三点影响&#xff1a; 下载小游戏首包数据文件下载和编译wasm代码引擎初始化…...

Leetcode二叉树刷题

给你一个二叉树的根节点 root &#xff0c; 检查它是否轴对称。 示例 1&#xff1a; 输入&#xff1a;root [1,2,2,3,4,4,3] 输出&#xff1a;true public boolean isSymmetric(TreeNode root) {if(rootnull)return true;return compare(root.left,root.right);}public boole…...

Java 8 Stream API 入门到实践详解

一、告别 for 循环&#xff01; 传统痛点&#xff1a; Java 8 之前&#xff0c;集合操作离不开冗长的 for 循环和匿名类。例如&#xff0c;过滤列表中的偶数&#xff1a; List<Integer> list Arrays.asList(1, 2, 3, 4, 5); List<Integer> evens new ArrayList…...

多场景 OkHttpClient 管理器 - Android 网络通信解决方案

下面是一个完整的 Android 实现&#xff0c;展示如何创建和管理多个 OkHttpClient 实例&#xff0c;分别用于长连接、普通 HTTP 请求和文件下载场景。 <?xml version"1.0" encoding"utf-8"?> <LinearLayout xmlns:android"http://schemas…...

HTML 列表、表格、表单

1 列表标签 作用&#xff1a;布局内容排列整齐的区域 列表分类&#xff1a;无序列表、有序列表、定义列表。 例如&#xff1a; 1.1 无序列表 标签&#xff1a;ul 嵌套 li&#xff0c;ul是无序列表&#xff0c;li是列表条目。 注意事项&#xff1a; ul 标签里面只能包裹 li…...

电脑插入多块移动硬盘后经常出现卡顿和蓝屏

当电脑在插入多块移动硬盘后频繁出现卡顿和蓝屏问题时&#xff0c;可能涉及硬件资源冲突、驱动兼容性、供电不足或系统设置等多方面原因。以下是逐步排查和解决方案&#xff1a; 1. 检查电源供电问题 问题原因&#xff1a;多块移动硬盘同时运行可能导致USB接口供电不足&#x…...

学校时钟系统,标准考场时钟系统,AI亮相2025高考,赛思时钟系统为教育公平筑起“精准防线”

2025年#高考 将在近日拉开帷幕&#xff0c;#AI 监考一度冲上热搜。当AI深度融入高考&#xff0c;#时间同步 不再是辅助功能&#xff0c;而是决定AI监考系统成败的“生命线”。 AI亮相2025高考&#xff0c;40种异常行为0.5秒精准识别 2025年高考即将拉开帷幕&#xff0c;江西、…...

JS设计模式(4):观察者模式

JS设计模式(4):观察者模式 一、引入 在开发中&#xff0c;我们经常会遇到这样的场景&#xff1a;一个对象的状态变化需要自动通知其他对象&#xff0c;比如&#xff1a; 电商平台中&#xff0c;商品库存变化时需要通知所有订阅该商品的用户&#xff1b;新闻网站中&#xff0…...

【Linux】Linux 系统默认的目录及作用说明

博主介绍&#xff1a;✌全网粉丝23W&#xff0c;CSDN博客专家、Java领域优质创作者&#xff0c;掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java技术领域✌ 技术范围&#xff1a;SpringBoot、SpringCloud、Vue、SSM、HTML、Nodejs、Python、MySQL、PostgreSQL、大数据、物…...

android RelativeLayout布局

<?xml version"1.0" encoding"utf-8"?> <RelativeLayout xmlns:android"http://schemas.android.com/apk/res/android"android:layout_width"match_parent"android:layout_height"match_parent"android:gravity&…...

如何在Windows本机安装Python并确保与Python.NET兼容

✅作者简介&#xff1a;2022年博客新星 第八。热爱国学的Java后端开发者&#xff0c;修心和技术同步精进。 &#x1f34e;个人主页&#xff1a;Java Fans的博客 &#x1f34a;个人信条&#xff1a;不迁怒&#xff0c;不贰过。小知识&#xff0c;大智慧。 &#x1f49e;当前专栏…...

【题解-洛谷】P10480 可达性统计

题目&#xff1a;P10480 可达性统计 题目描述 给定一张 N N N 个点 M M M 条边的有向无环图&#xff0c;分别统计从每个点出发能够到达的点的数量。 输入格式 第一行两个整数 N , M N,M N,M&#xff0c;接下来 M M M 行每行两个整数 x , y x,y x,y&#xff0c;表示从 …...