GO Ants 学习
文章目录
- 主要特性
- 安装
- 基本用法
- 1. 创建协程池并提交任务
- 2. 带返回值的任务提交
- 3. 自定义协程池的参数
- 4. 获取协程池状态
- 应用场景
- 优势
- 资源释放
- 性能对比
- 总结
ants
是一个高性能的 Go 语言协程池库,专注于有效地管理 Go 协程的数量。它通过复用协程减少了创建和销毁协程带来的性能开销,特别适合在高并发场景下使用。相比于直接使用 Go 的原生协程,
ants
提供了更细粒度的控制,并且可以极大减少内存消耗。
GitHub 仓库:ants
主要特性
- 高性能:通过协程池技术减少内存分配,提升系统性能。
- 自动伸缩:可以根据当前任务数动态调整池中协程数量。
- 任务超时控制:支持为任务设置超时时间,超时未完成的任务可以被取消。
- 多种提交任务方式:支持异步任务提交,带返回值的任务提交。
- 资源复用:通过复用协程来避免频繁创建和销毁协程,节省系统资源。
安装
使用 go get
来安装 ants
:
go get -u github.com/panjf2000/ants
基本用法
1. 创建协程池并提交任务
通过 ants.NewPool
来创建一个具有固定大小的协程池。然后可以使用 Submit
方法向协程池中提交任务。
package main
import (
"fmt"
"sync"
"time"
"github.com/panjf2000/ants"
)
func main() {
var wg sync.WaitGroup
// 创建一个容量为 10 的协程池
pool, _ := ants.NewPool(10)
defer pool.Release() // 在程序结束时释放协程池资源
// 提交任务到协程池
for i := 0; i < 100; i++ {
wg.Add(1)
// 使用 Submit 方法提交任务
pool.Submit(func() {
time.Sleep(100 * time.Millisecond)
fmt.Println("任务完成")
wg.Done()
})
}
// 等待所有任务完成
wg.Wait()
fmt.Println("所有任务已完成")
}
2. 带返回值的任务提交
除了简单的任务提交外,ants
还支持带返回值的任务。可以通过 ants.PoolWithFunc
创建协程池,并使用 Invoke
方法提交任务。
package main
import (
"fmt"
"sync"
"github.com/panjf2000/ants"
)
func main() {
var wg sync.WaitGroup
// 创建带有返回值的协程池
pool, _ := ants.NewPoolWithFunc(10, func(i interface{}) {
fmt.Println(i)
wg.Done()
})
defer pool.Release()
// 提交任务
for i := 0; i < 10; i++ {
wg.Add(1)
pool.Invoke(i) // 使用 Invoke 提交带有参数的任务
}
// 等待所有任务完成
wg.Wait()
fmt.Println("所有任务已完成")
}
3. 自定义协程池的参数
可以通过 NewPool
方法传入自定义参数,例如最大协程数量、超时时间等。
package main
import (
"fmt"
"sync"
"time"
"github.com/panjf2000/ants"
)
func main() {
var wg sync.WaitGroup
// 自定义协程池参数:最大协程数为 5,最大空闲时间为 10 秒
pool, _ := ants.NewPool(5, ants.WithExpiryDuration(10*time.Second))
defer pool.Release()
for i := 0; i < 10; i++ {
wg.Add(1)
pool.Submit(func() {
time.Sleep(1 * time.Second)
fmt.Println("任务完成")
wg.Done()
})
}
wg.Wait()
}
4. 获取协程池状态
ants
提供了一些方法来获取协程池的状态,比如当前池中活跃的协程数量等。
fmt.Printf("运行中的协程数:%d\n", pool.Running()) // 获取正在执行任务的协程数量
fmt.Printf("协程池容量:%d\n", pool.Cap()) // 获取协程池的最大容量
fmt.Printf("空闲协程数:%d\n", pool.Free()) // 获取当前空闲的协程数量
应用场景
- 高并发任务处理:通过协程池有效地管理并发任务数,避免大量协程占用过多资源。
- 爬虫系统:可以用
ants
协程池并发处理多个请求,爬取网页数据,控制并发数避免对服务器产生过大压力。 - 批量任务执行:适合批量处理任务的场景,比如图像处理、数据处理等。
- 服务端请求处理:在高并发服务端应用中,
ants
协程池可以帮助限制同时处理的请求数量,减少内存占用。
优势
- 高性能:通过减少协程的频繁创建和销毁,
ants
可以显著提升程序的执行效率。 - 内存占用低:复用协程可以有效减少内存开销,尤其在高并发场景中表现尤为显著。
- 自动伸缩:可以根据任务数动态调整协程数量,保证系统资源的最优利用。
资源释放
使用 ants
时,创建协程池后应该在使用完毕后调用 Release()
方法释放资源。
pool.Release() // 在程序结束或不再需要时调用
性能对比
ants
在并发性能和内存使用上优于直接使用 Go 的原生协程。根据其官方的性能测试结果,ants
能显著减少 Goroutine 的创建和销毁带来的资源开销,特别是在高并发、大量短生命周期任务的场景下表现优秀。
总结
ants
是一个非常高效的 Go 协程池库,适合在高并发场景下进行任务调度和协程管理。通过它可以显著减少内存和 CPU 的消耗,同时提供了灵活的任务提交和管理方式,适用于各类并发任务处理的场景。