我尝试着用多线程分别运行以下两个函数,并使用 time
来查看它们的 cpu 使用率,一个的使用率就符合启动的线程数(比如 8 线程就得到 800% 的使用率),另一个就无法得到相符合的 cpu 使用率 (比如 8 线程得到 600% 的使用率,2 线程得到 300% 的使用率)。虽然两个函数都没有线程间的互斥锁,这两个函数的区别在于:第一个函数没有对数组的操作,第二个函数有对数组的操作。具体函数如下:
函数 1: addOne
该函数持续做加法运算
func addOne(n int,wg *sync.WaitGroup){
var i int
for i < n{
i++
}
wg.Done()
}
函数 2: appendArray
该函数不断向一个数组中添加元素,为了防止内存溢出,每添加 10,000 个元素,就清空数组。
func appendArray(n int,wg *sync.WaitGroup){
var i int
list := make([]int,10000)
for i < n{
for j := 0 ; j < 10000; j++{
list = append(list, i)
}
list = make([]int,10000)
i++
}
wg.Done()
}
启动多线程的函数: test
该函数将工作总数 totalJobs
平分给每个线程
func test(totalThreads, totalJobs int){
n := totalJobs/totalThreads
var wg sync.WaitGroup
for i := 0; i < totalThreads; i++{
wg.Add(1)
go appendArray(n,&wg)
// go addOne(n,&wg)
}
wg.Wait()
}
通过使用 pprof
, 两个代码的 cpu 分析如下:
函数 1:
函数 2:
我发现对于第二个函数,虽然代码中没有调用锁,在执行的过程中会出现 runtime lock
, runtime futex
之类的锁操作。
这里我不明白的是:
这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。
V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。
V2EX is a community of developers, designers and creative people.