改装 1024 真的比改装 1023 快吗?
Posted
技术标签:
【中文标题】改装 1024 真的比改装 1023 快吗?【英文标题】:Is modding 1024 really faster than modding 1023? 【发布时间】:2022-01-22 22:24:32 【问题描述】:我的同事告诉我,代码修改 2 的功能将针对位操作进行优化,并且比修改其他数字更快。我已经检查了证明他的选择的程序集。但是我用 Golang 编写了一个基准代码,并使用 Go 1.17 版本运行它。似乎没有太大区别。为什么会这样?他说的对吗?
这里是 Golang 代码:
package main
import (
"fmt"
"time"
)
const loop = 10000000000
func Mod1024() int
sum := 0
for i := 0; i < loop; i++
sum += i % 1024
return sum
func Mod1023() int
sum := 0
for i := 0; i < loop; i++
sum += i % 1023
return sum
func main()
start := time.Now()
Mod1023()
fmt.Println(time.Since(start).Microseconds())
start = time.Now()
Mod1024()
fmt.Println(time.Since(start).Microseconds())
我电脑上的结果是:
2810668
2694136
【问题讨论】:
【参考方案1】:执行单个模运算真的很快,它在单个纳秒的量级。您的Mod1024()
和Mod1023()
函数所做的更多:它们递增和测试循环变量,执行加法并将结果存储在局部变量中。无论是否针对位掩码进行了优化,这些都比简单的修改操作高出几个数量级。
此外,将任何代码作为主应用程序的一部分进行基准测试绝不是一个好主意,有许多因素会扭曲结果(通常使其完全无用)。见Order of the code and performance。始终使用 Go 的测试框架(具有基准测试功能)来更可靠地对代码进行基准测试。
所以让我们修改示例函数:
func Mod1023()
for i := 23; i%1023 != 0; i++
func Mod1024()
for i := 24; i%1024 != 0; i++
(上述函数中的循环将有1000次迭代。)
让我们使用 Go 的测试框架编写适当的基准测试函数:
func BenchmarkMod1023(b *testing.B)
for i := 0; i < b.N; i++
Mod1023()
func BenchmarkMod1024(b *testing.B)
for i := 0; i < b.N; i++
Mod1024()
使用go test -bench .
运行基准测试,输出为:
BenchmarkMod1023-8 881263 1346 ns/op
BenchmarkMod1024-8 3710430 325.4 ns/op
所以是的,1024
的修改已针对位掩码进行了优化,实际上速度更快:大约 快 4 倍。由于优化(1.3 ns vs 0.3 ns),为您节省了整整纳秒。尽管这仅在您必须执行数百万次且执行过程中没有其他代码比简单的 CPU mod 操作慢时才重要。
【讨论】:
以上是关于改装 1024 真的比改装 1023 快吗?的主要内容,如果未能解决你的问题,请参考以下文章