🔥码云GVP开源项目 12k star Uniapp+ElementUI 功能强大 支持多语言、二开方便! 广告
共享内存并发机制 === > 像java这样的语言实现并发就涉及共享资源,为了保证资源的安全性就要用到锁 go 并发之间的通讯可以用channel吧并行数据转变为串行数据,我们还是向讲一讲老的处理方案 ### Package Sync包中有两个锁 一个是Mutex 互斥写锁 一个是RWLock 读写锁 没有锁的下场 ~~~ func TestCounter(t *testing.T) { counter := 0 var wg sync.WaitGroup for i := 0;i<5000;i++ { wg.Add(1) go func() { counter++ wg.Done() }() } wg.Wait() t.Log(counter) } ~~~ ![](https://box.kancloud.cn/00a94ed3dbda3f69129ecb46a08cc42a_729x631.png) 这个根本就不对阿! 哈哈哈 有可能几个协程同时写导致的 所以我们要使用锁来实现 我们向计算以下这个程序的时间 ~~~ func TestCounter(t *testing.T) { nowTime := time.Now().UnixNano() counter := 0 var wg sync.WaitGroup for i := 0;i<5000;i++ { wg.Add(1) go func() { counter++ wg.Done() }() } wg.Wait() t.Log(counter) tTime := time.Now().UnixNano() fmt.Println("time: ",(tTime - nowTime)) } ~~~ 这里用nano秒来计算,为什么了go太快了 现在测试结果是: ``` === RUN TestCounter time: 2071910 --- PASS: TestCounter (0.00s) share_test.go:28: 4334 PASS ``` ### 我们现在加上锁 ~~~ func TestMutCounter(t *testing.T) { nowTime := time.Now().UnixNano() var nut sync.Mutex counter := 0 var wg sync.WaitGroup for i := 0;i<5000;i++ { wg.Add(1) go func() { nut.Lock() defer nut.Unlock() counter++ wg.Done() }() } wg.Wait() t.Log(counter) tTime := time.Now().UnixNano() fmt.Println("time: ",(tTime - nowTime)) } ~~~ 现在的返回结果 ``` === RUN TestMutCounter time: 2151931 --- PASS: TestMutCounter (0.00s) share_test.go:48: 5000 PASS ``` 答案是对了但是大家有没有发现这个时间,比上一个没有加锁的时间多 这个就锁带来的性能消耗 为了解决这个问题我们用读写锁来实现一遍 看下面的RWMutex