内容简介:Mutex是一个互斥锁,可以创建为其他结构体的字段;零值为解锁状态。Mutex类型的锁和线程无关,可以由不同的线程加锁和解锁。• 它只有两个公开方法:Lock()加锁,unlock()解锁。• 在同一个协程中加锁后,不能再继续对其加锁,否则会panic。只有在解锁之后才能再次加锁。
Go语言包中的sync包提供了两种锁,互斥锁(sync.Mutex)和读写锁(sync.RWMutex)
这一篇博文我们只说一下互斥锁。
Mutex是一个互斥锁,可以创建为其他结构体的字段;零值为解锁状态。Mutex类型的锁和线程无关,可以由不同的线程加锁和解锁。
• 它只有两个公开方法:Lock()加锁,unlock()解锁。
• 在同一个协程中加锁后,不能再继续对其加锁,否则会panic。只有在解锁之后才能再次加锁。
• 只允许只有一个读或者写的场景
• 在使用Unlock()解锁前,未使用Lock()加锁,就会引起一个运行错误。
函数原型
func (m *Mutex) Lock()
Lock方法锁住m,如果m已经加锁,则阻塞直到m解锁。
func (m *Mutex) Unlock()
Unlock方法解锁m,如果m未加锁会导致运行时错误。锁和线程无关,可以由不同的线程加锁和解锁。
一个例子理解互斥锁的作用
package main
import (
"fmt"
"sync"
)
var num = 0
func increment(wg *sync.WaitGroup) {
num = num + 1
wg.Done()
}
func main() {
var w sync.WaitGroup
for i := 0; i < 1000; i++ {
w.Add(1)
//开启协程
go increment(&w)
}
w.Wait()
fmt.Println("num =", num)
}
在上述程序中,调用1000个协程来进行num=num+1操作
运行几次的输出分别为
num = 971
num = 944
num = 959
每次运行都没有达到预期的效果,因为多个并发的协程试图访问 num 的值,这时就会发生竞态条件。
现在我们可以对上述程序加上锁,每次只能由一个线程来操作num的值
package main
import (
"fmt"
"sync"
)
var num = 0
func increment(wg *sync.WaitGroup, m *sync.Mutex) {
//互斥锁
m.Lock() //当有线程进去进行加锁
num = num + 1
m.Unlock() //出来后解锁,其他线程才可以进去
wg.Done()
}
var w sync.WaitGroup
var m sync.Mutex
for i := 0; i < 1000; i++ {
w.Add(1)
go increment(&w, &m)//这里要传引用并不能传值,如果传值,那么每个协程都会得到 Mutex 的一份拷贝,竞态条件还是会发生。
}
w.Wait()
fmt.Println("num =", num)
输出
num = 1000
我们也可以使用缓冲信道来实现互斥锁
func increment2(wg *sync.WaitGroup, b chan bool) {
//自定义互斥锁
b <- true
num = num + 1
<-b
wg.Done()
}
func main() {
var w sync.WaitGroup
ch := make(chan bool,1)
for i := 0; i < 1000; i++ {
w.Add(1)
go increment2(&w, ch)
}
w.Wait()
fmt.Println("num =", num)
}
输出
num = 1000
func main() {
wa := sync.WaitGroup{}
var mu sync.Mutex
fmt.Println("加锁0")
mu.Lock()
fmt.Printf("上锁中0\t")
for i := 1; i < 4; i++ {
wa.Add(1)
go func(i int) {
fmt.Printf("加锁%d\t", i)
mu.Lock()
fmt.Printf("上锁中%d\t", i)
time.Sleep(time.Second * 1)
mu.Unlock()
fmt.Printf("解锁%d\t", i)
wa.Done()
}(i)
}
time.Sleep(time.Second * 5)
mu.Unlock()
fmt.Println("\n解锁0")
wa.Wait()
}
输出为
加锁0
上锁中0 加锁2 加锁3 加锁1 上锁中2
解锁0
解锁2 上锁中3 解锁3 上锁中1 解锁1
以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,也希望大家多多支持 码农网
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
The Master Switch
Tim Wu / Knopf / 2010-11-2 / USD 27.95
In this age of an open Internet, it is easy to forget that every American information industry, beginning with the telephone, has eventually been taken captive by some ruthless monopoly or cartel. Wit......一起来看看 《The Master Switch》 这本书的介绍吧!