背景
在工作中经常会遇到对于linux随机数生产原理不熟悉的同事,直接使用伪随机,造成最终生产上实现对实际的需求不符,导致各种生产事故。
rand库
golang生产随机数的算法库有两个: math/rand(伪随机) crypto/rand(真随机)
- math/rand
原理伪随机生成的数字是确定的,不论在什么机器、什么时间,只要执行的随机代码一样,那么生成的随机数序列就一样,例如:
一般应用于游戏中的概率事件,这样客户端与服务端生产的随机序列是一致的。 - crypto/rand
为了提供更好的随机性满足密码对随机数的要求,在linux上已经有一个实现就是/dev/urandom,crypto/rand 就是从这个地方读“真随机”数字返回,但性能比较慢。
- 性能对比(接近10倍)
name time/op
RandWithCrypto-8 272ns ± 3%
name time/op
RandWithMath-8 22.8ns ± 4%
- 应用场景
对于普通的开发场景,可以选择使用math/rand加seed的方法来产生随机数序列。rand.Seed(time.Now().UnixNano())
对于加密要求较高的场景,建议使用crypto/rand。