func Benchmark_foreach1(b *testing.B) {
var test map[int]int
test = make(map[int]int)
for i := 0; i < 100000; i++ {
test[i] = 1
}
for i := 0; i < b.N; i++ {
for i, _ := range test {
if test[i] != 1 {
panic("ds")
}
}
}
}
func Benchmark_foreach2(b *testing.B) {
var test map[int]int
test = make(map[int]int)
for i := 0; i < 100000; i++ {
test[i] = 1
}
for i := 0; i < b.N; i++ {
for _, v := range test {
if v != 1 {
panic("heh")
}
}
}
}运行结果如下
goos: linux
goarch: amd64
Benchmark_foreach1-2 500 3172323 ns/op
Benchmark_foreach2-2 1000 1707214 ns/op为什么foreach-2慢?
发布于 2017-11-06 12:20:03
我认为Benchmark_foreach2-2大约快2倍--每次操作需要1707214纳秒,第一次需要3172323纳秒。所以第二个问题是3172323 / 1707214 = 1.85的速度快了一倍。
原因:第二,不再需要从内存中获取值,它已经在v变量中使用了值。
发布于 2017-11-06 12:42:59
test[k]语句在BenchmarkForeachK中随机读取值需要时间,因此BenchmarkForeachK比BenchmarkForeachV花费的时间更长,为9362945 ns/op,而BenchmarkForeachV为4213940 ns/op。
例如,
package main
import "testing"
func testMap() map[int]int {
test := make(map[int]int)
for i := 0; i < 100000; i++ {
test[i] = 1
}
return test
}
func BenchmarkForeachK(b *testing.B) {
test := testMap()
b.ReportAllocs()
b.ResetTimer()
for i := 0; i < b.N; i++ {
for k := range test {
if test[k] != 1 {
panic("eh")
}
}
}
}
func BenchmarkForeachV(b *testing.B) {
test := testMap()
b.ReportAllocs()
b.ResetTimer()
for i := 0; i < b.N; i++ {
for _, v := range test {
if v != 1 {
panic("heh")
}
}
}
}输出:
$ go test foreach_test.go -bench=.
BenchmarkForeachK-4 200 9362945 ns/op 0 B/op 0 allocs/op
BenchmarkForeachV-4 300 4213940 ns/op 0 B/op 0 allocs/ophttps://stackoverflow.com/questions/47136838
复制相似问题