typora/note/Go/通信并发.md
2024-12-12 10:48:55 +08:00

34 lines
2.6 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

### 并发&&并行
- 并发不是并行
- 并发是应用结构设计相关的概念,而并行只是程序执行期的概念
- 并行的必要条件是具有多个处理器或多核处理器,否则无论是否是并发的设计,程序执行时都有且仅有一个任务可以被调度到处理器上执行
### Go并发方案
- Go 的并发方案goroutine
- Go 并没有使用操作系统线程作为承载分解后的代码片段(模块)的基本执行单元
- 实现了goroutine这一由 Go 运行时runtime负责调度的、轻量的用户级线程为并发程序设计提供原生支持
- 无论是 Go 自身运行时代码还是用户层 Go 代码,都无一例外地运行在 goroutine 中
### goroutine优势
- 资源占用小,每个 goroutine 的初始栈大小仅为 2k
- 由 Go 运行时而不是操作系统调度goroutine 上下文切换在用户层完成,开销更小
- 在语言层面而不是通过标准库提供。goroutine 由go关键字创建一退出就会被回收或销毁开发体验更佳
- 语言内置 channel 作为 goroutine 间通信原语,为并发设计提供了强大支撑
### goroutine使用
#### 创建goroutine
- Go 语言通过go关键字+函数/方法的方式创建一个 goroutine
- Go 也可以基于匿名函数 / 闭包创建 goroutine
- 创建 goroutine 后go 关键字不会返回 goroutine id 之类的唯一标识 goroutine 的 id
- 一个应用内部启动的所有 goroutine 共享进程空间的资源,如果多个 goroutine 访问同一块内存数据,将会存在竞争,需要进行 goroutine 间的同步
- 创建后,新 goroutine 将拥有独立的代码执行流,并与创建它的 goroutine 一起被 Go 运行时调度
#### 退出goroutine
- goroutine 的执行函数的返回,就意味着 goroutine 退出goroutine 执行的函数或方法即便有返回值Go 也会忽略这些返回值,如果需要返回值,通过 goroutine 间的通信来实现
- main goroutine 退出那么也意味着整个应用程序的退出其他的goroutine也就都退出
#### goroutine间的通信
> 操作系统线程间的通信方式共享内存、信号signal、管道pipe、消息队列、套接字socket基于对内存的共享的
- channel 符合`CSPCommunicationing Sequential Processes通信顺序进程`模型的通信方式,通过使用 channel 将goroutine组合在一起
- Go 也支持传统的、基于共享内存的并发模型,并提供了基本的低级别同步原语(主要是 sync 包中的互斥锁、条件变量、读写锁、原子操作等)