协程并发(并行)资源竞争问题 | 学习笔记

简介: 快速学习协程并发(并行)资源竞争问题

开发者学堂课程【Go语言核心编程 - 面向对象、文件、单元测试、反射、TCP编程协程并发(并行)资源竞争问题】学习笔记,与课程紧密联系,让用户快速学习知识。

课程地址:https://developer.aliyun.com/learning/course/626/detail/9751


协程并发(并行)资源竞争问题

一,channel(管道)-看个需求

把这些数的阶层放入到 map 中,最后显示出来要求使用 go green 来完成。实际上它就是用携程去做,使用这个greeting 来完成效率高,但是会出现一个并发和并行安全的问题。使用第一步,使用 growth 来完成,看看 growing并发会出现什么问题。然后去解决第一步。第二步,再运行某个程序时,如何知道是否存在资源竞争的问题。这个资源竞争怎么去做,在编译的时候,可以加个 race,这个时候我们还是新建一个文件夹。

需求:现在要计算1-200的各个数的阶乘,并且把各个数的阶乘放入到 map 中。最后显示出来。要求使用 goroutine 完成
分析思路:
使用 goroutine 来完成,效率高,但是会出现并发/并行安全问题,2) 这里就提出了不同 goroutine 如何通信的问题。
代码实现
使用 goroutine 来完成(看看使用 gorotine 并发完成会出现什么问题然后去解决)
在运行某个程序时,如何知道是否存在资源竞争问题。方法很简单,在编译该程序时,增加一个参数 race 即可。

第一步:先填需求

package mainimport  ("fmt”


//需求:现在要计算1-200的各个数的阶乘,并且把各个数的阶乘放入到 map 中。
//最后显示出来。要求使用 goroutine 完成
说明思路:

1.编写一个函数,来计算各个数的阶乘,并放入到 map 中.
2.我们启动的协程多个,统计的将结果放入到 map 
3. map 应该做出一个全局的.

第二步:将得到的结果放进去
var (myMap = make(map[int]int, 10)

第三步:如何将数传进去

//test 函数就是计算 n!, 让将这个结果放入到 myMap
func test() {

res : = 1res * = 1for i : = 1; I <= n; i++ {

}

//这里我们将 res 放入到 myMap

说明:这里容易出现保护机制

myMap[n] = res //concurrent  map writes?

}func main() {

说明:将 n 往 map 里放,

第四步:有多少个任务填多少个

//我们这里开启多个协程完成这个任务[200个]
for i : = 1; I <= 200; i++ {

go test(i)

}

说明:相当于有200个来进行工作

//这里我们输出结果,变量这个结果
for i, v  :=  range myMap{fmt.Printf("map[%d]=%d\n", i, v)

}

}

最后运行时可能错误

在第四步加入:

//休眠10秒钟【?】

time.sleep(time.second*10)

image.png

输出结果会出现一个经典错误

map[19]=0map[74]=0map[40]=-70609262346240000map[90]=0map[132]=0map[2001]=0map[153]=0map[166]=0map[18]=6402373705728000map[50]=-3258495067890909184mmap[122 ]=0map[129]=0map[159]=0map[77]=0map[41]=2894979756195840000mmap[109 ]=0map[1201]=0map[133]=0map[195]m0map[151]m0Found 4 data race<s>

说明:最后说发现有四个数据就是它可以准确告诉你其实在写的数据整理有四个数据产生官网,里面写出问题没有地方。已经有结果了,但是,有四个数据,产生一个竞争关系,这个就可能出现问题来解决这个竞争关系问题。

相关文章
|
2月前
|
安全 Go
Golang语言goroutine协程并发安全及锁机制
这篇文章是关于Go语言中多协程操作同一数据问题、互斥锁Mutex和读写互斥锁RWMutex的详细介绍及使用案例,涵盖了如何使用这些同步原语来解决并发访问共享资源时的数据安全问题。
86 4
|
1月前
|
安全 Go 调度
探索Go语言的并发模式:协程与通道的协同作用
Go语言以其并发能力闻名于世,而协程(goroutine)和通道(channel)是实现并发的两大利器。本文将深入了解Go语言中协程的轻量级特性,探讨如何利用通道进行协程间的安全通信,并通过实际案例演示如何将这两者结合起来,构建高效且可靠的并发系统。
|
2月前
|
数据采集 消息中间件 并行计算
进程、线程与协程:并发执行的三种重要概念与应用
进程、线程与协程:并发执行的三种重要概念与应用
60 0
|
3月前
|
监控 Devops 测试技术
|
4月前
|
消息中间件 算法 Java
(十四)深入并发之线程、进程、纤程、协程、管程与死锁、活锁、锁饥饿详解
本文深入探讨了并发编程的关键概念和技术挑战。首先介绍了进程、线程、纤程、协程、管程等概念,强调了这些概念是如何随多核时代的到来而演变的,以满足高性能计算的需求。随后,文章详细解释了死锁、活锁与锁饥饿等问题,通过生动的例子帮助理解这些现象,并提供了预防和解决这些问题的方法。最后,通过一个具体的死锁示例代码展示了如何在实践中遇到并发问题,并提供了几种常用的工具和技术来诊断和解决这些问题。本文旨在为并发编程的实践者提供一个全面的理解框架,帮助他们在开发过程中更好地处理并发问题。
|
5月前
|
安全 Android开发 Kotlin
Android面试题之Kotlin协程并发问题和互斥锁
Kotlin的协程提供轻量级并发解决方案,如`kotlinx.coroutines`库。`Mutex`用于同步,确保单个协程访问共享资源。示例展示了`withLock()`、`lock()`、`unlock()`和`tryLock()`的用法,这些方法帮助在协程中实现线程安全,防止数据竞争。
76 1
|
4月前
|
Java Go 调度
Java演进问题之协程和线程在资源占用和切换速度上不同如何解决
Java演进问题之协程和线程在资源占用和切换速度上不同如何解决
|
5月前
|
监控 程序员 调度
协程实现单线程并发(入门)
协程实现单线程并发(入门)
63 1
|
6月前
|
存储 Python
python使用gevent库来创建协程,并通过协程实现并发执行不同的任务
```markdown 这段Python代码利用`gevent`库实现并发执行协程。定义了两个打印函数`f1`和`f2`,分别输出&quot;csdn&quot;和&quot;yyds&quot;。代码首先创建列表`t_l`,并启动5个`f1`协程,将其加入列表并等待所有协程完成。随后,同样方式启动5个`f2`协程,存入`t1_l`列表并等待执行完毕。整体展示了`gevent`的协程并发操作。 ```
57 1
|
6月前
|
程序员 Go 数据处理