并发&并行(多任务处理方式)
- 并发是在单核上运行的,通过切换时间片实现同时运行,每个人任务不必等待其他任务执行完才开始执行。
- 并行则在多核CPU、多CPU或分布式计算上,多个任务在同一时刻同时运行,每个任务都可以访问到计算机系统中的不同资源。
- PS:
- 在并发模型中,多个任务经常同时访问一个资源,需要避免资源竞争和竞争条件问题,否则可能会导致死锁和饥饿等问题。
- 在并行模型中,如果多个任务之间存在依赖关系,可能会导致数据一致性问题和同步问题,可使用锁机制和原子操作等方法,确保并行处理的正确性。
Goroutine(轻量级线程,也叫协程)
Goroutine是Go语言实现高并发的关键机制之一。
使用关键字go就可以创建协程
CSP(通信顺序进程模型)
CSP描述的是两个独立的并发实体通过共享的通信信道进行通信的并发模型,并非通过共享内存实现通信,这也不是CSP所提倡的,但如果想要通过共享内存实现通信,需要通过互斥量加锁方式实现。
Channel
通过make(chan 元素类型,[缓冲大小])
根据是否有缓冲大小分为有缓冲通道和无缓冲通道
- 无缓冲通道 make(chan,int)发送和接收是同步的
- 有缓冲通道 make(chan,int,2)
线程和协程的区别
- 线程的切换需要进入内核,然后进行上下文切换;协程在用户态下完成,不需要进入内核态。
- 在Go语言中协程是轻量级的,内存是KB级别,而线程是MB级别
GOPATH
- 环境变量$GOPATH
- 项目代码直接依赖src下的代码
- go get
弊端:无法实现package的多版本控制
GO Vendor
- 项目目录下增加vendor文件,所有依赖包副本形式放在$ProjectRoot/vendor
- 依赖寻址方式:vendor => GOPATH
通过每个项目引入一份依赖的副本,解决了多个项目需要同一个package依赖的冲突问题。
弊端:
- 无法控制依赖的版本
- 更新项目有可能出现依赖冲突,导致编译出错
Go Module ——定义版本规则和管理项目依赖关系
- 通过go.mod文件管理依赖包版本
- 通过go get/go mod指令工具管理依赖包
依赖管理三要素
- 配置文件,描述依赖 go.mod
- 中心仓库管理依赖库 Proxy
- 本地工具 go get/mod
单元测试
规则:
- 所有测试文件以_test.go结尾
- func TestXxx(*testing.T)
- 初始化逻辑放到TestMain中
- assert断言单元测试
- 单元测试覆盖率:代码是否有执行
Tips:
- 一般覆盖率;50%-60%,较高覆盖率80%+
- 测试分支相互独立、全面覆盖
- 测试单元粒度足够小,函数单一职责
- 幂等:每次重复运行一个测试,返回结果一致
- 稳定;单元测试在任何时间,代码任意行独立运行
快速Mock函数
- 为一个函数打桩
- 为一个方法打桩
基准测试(例子 -> 运行 -> 优化) 例子:rand保证全局随机性和并发安全,持有全局锁,降低了并发的性能 优化:fastrand——牺牲了随机数列的一致性,适用于大多数场景
分层结构
- 数据层:数据Model,处理外部数据增删改查
- 逻辑层:业务Enitity,处理核心业务逻辑输出
- 视图层:视图View,处理和外部交互的逻辑