【密码学】一文读懂MT19937

本文涉及的产品
Redis 开源版,标准版 2GB
推荐场景:
搭建游戏排行榜
云数据库 Tair(兼容Redis),内存型 2GB
文档翻译,文档翻译 1千页
简介: 瞄了一眼redis的源码,然后发现里面好玩的东西还挺多的,本文来聊一聊redis当中用到的一个随机数生成算法 mt19937,具体源码参见文末的参考资料,在这里就不贴到文本当中了。对于redis源码里面用的是mt19937-64本文先来看一下32位的版本,对于64位的版本,只不过状态当中元素用的是64位的元素,整个运算过程框架是类似的。「梅森旋转算法」(「Mersenne twister」)是一个伪随机数生成算法,由松本真和西村拓士在1997年提出来的,可以快速产生高质量的伪随机数,修正了古典随机数生成算法当中的很多缺陷。19937这个名字来源于周期长度为梅森素数 。

【密码学】一文读懂MT19937


]MO$QND[_P_8_@G]TCR8GZI.jpg

瞄了一眼redis的源码,然后发现里面好玩的东西还挺多的,本文来聊一聊redis当中用到的一个随机数生成算法 mt19937,具体源码参见文末的参考资料,在这里就不贴到文本当中了。对于redis源码里面用的是mt19937-64本文先来看一下32位的版本,对于64位的版本,只不过状态当中元素用的是64位的元素,整个运算过程框架是类似的。

「梅森旋转算法」「Mersenne twister」)是一个伪随机数生成算法,由松本真和西村拓士在1997年提出来的,可以快速产生高质量的伪随机数,修正了古典随机数生成算法当中的很多缺陷。19937这个名字来源于周期长度为梅森素数 。


生成器结构

OBAK1U[T7G]C@CA0)UAVAKD.pngMT19937生成器结构

如上图所示,mt19937的随机数生成器结构首先需要一个uint32的种子,然后生成一个具有624个uint32数组的状态数组。生成状态数组之后,进行一次旋转,最终可以输出624个随机的uint32。然后重复执行旋转操作,就可以得到一个周期为 的随机数生成器了。

对于mt19937整个计算过程来说,虽然比我之前提到过的线性同余法复杂不少,但是整个流程还是比较清晰的,对于里面的原理,我其实也了解的不是很多,因此在这里就不展开讲了,如果想了解原理的读者,可以参考文末的参考资料当中的论文进行学习,本文是指来聊一下这个东西具体是怎么计算的。到这里,这篇文章我就水完了,逃~~~


代码实现

老样子了,还是给出我写的两个语言的参考,注意本文讲的是32位的mt19937,再去看redis源码当中的实现的时候用的是mt19937-64。

Go

const (
  n = 624
  m = 397
)
type MT19937 struct {
  state []uint32
  index int
}
func New(seed uint32) *MT19937 {
  mt := &MT19937{
    state: make([]uint32, n),
    index: 0,
  }
  mt.state[0] = seed
  for i := uint32(1); i < n; i++ {
    mt.state[i] = 1812433253*(mt.state[i-1]^mt.state[i-1]>>30) + i
  }
  return mt
}
func (mt *MT19937) twist() {
  for i := uint32(0); i < n; i++ {
    y := (mt.state[i] & 0x80000000) + (mt.state[(i+1)%n] & 0x7fffffff)
    mt.state[i] = (y >> 1) ^ mt.state[(i+m)%n]
    if y%2 != 0 {
      mt.state[i] = mt.state[i] ^ 0x9908b0df
    }
  }
}
func (mt *MT19937) Uint32() uint32 {
  if mt.index == 0 {
    mt.twist()
  }
  y := mt.state[mt.index]
  y = y ^ y>>11
  y = y ^ y<<7&2636928640
  y = y ^ y<<15&4022730752
  y = y ^ y>>18
  mt.index = (mt.index + 1) % n
  return y
}

Rust

const N: usize = 624;
struct MT19937 {
    state: [u32; N],
    index: usize,
}
impl MT19937 {
    pub fn new(seed: u32) -> Self {
        let mut mt = MT19937 {
            state: [0; N],
            index: 0,
        };
        mt.state[0] = seed;
        for i in 1..N {
            mt.state[i] = 1812433253 * (mt.state[i - 1] ^ (mt.state[i - 1] >> 30)) + i as u32;
        }
        mt
    }
    fn twist(&mut self) {
        for i in 0..N {
            let x = (self.state[i] & 0x80000000) | (self.state[(i + 1) % N] & 0x7fffffff);
            let mut x_a = x >> 1;
            if x % 2 != 0 {
                x_a ^= 0x9908b0df;
            }
            self.state[i] = self.state[(i + 397) % N] ^ x_a;
        }
        self.index = 0;
    }
    fn rand(&mut self) -> u32 {
        if self.index >= N {
            self.twist();
        }
        let y = self.state[self.index];
        self.index += 1;
        y ^ y >> 11
    }
}


相关文章
|
Web App开发 Rust 算法
【密码学】一文读懂ChaCha20
好久没写新的加密算法的原理了, 这次所选取的加密算法结构比较简单, 一起来看一下吧。
9407 1
【密码学】一文读懂ChaCha20
|
存储 算法 安全
【密码学】非对称加密算法 - ECDH
由于 ECC 密钥具有很短的长度,所以运算速度比较快。到目前为止,对于 ECC 进行逆操作还是很难的,数学上证明不可破解,ECC 算法的优势就是性能和安全性高。实际应用可以结合其他的公开密钥算法形成更快、更安全的公开密钥算法,比如结合 DH 密钥形成 ECDH 密钥协商算法,结合数字签名 DSA 算法组成 ECDSA 数字签名算法。ECDH算法常常用来进行密钥的协商,协商好密钥后,用来解决上面的密钥分配问题,将对称加密的密钥安全的传到对端设备。算法加密/解密数字签名密钥交换RSA✅✅✅❌。
4427 0
|
算法 安全 量子技术
【Python】蒙特卡洛模拟 | PRNG 伪随机数发生器 | 马特赛特旋转算法 | LCG 线性同余算法 | Python Random 模块
【Python】蒙特卡洛模拟 | PRNG 伪随机数发生器 | 马特赛特旋转算法 | LCG 线性同余算法 | Python Random 模块
673 0
|
算法 安全 程序员
【C++ 随机数生成器】深入解析C++ 随机数生成器mersenne_twister_engine等
【C++ 随机数生成器】深入解析C++ 随机数生成器mersenne_twister_engine等
660 0
|
机器学习/深度学习 并行计算 PyTorch
ONNX 优化技巧:加速模型推理
【8月更文第27天】ONNX (Open Neural Network Exchange) 是一个开放格式,用于表示机器学习模型,使模型能够在多种框架之间进行转换。ONNX Runtime (ORT) 是一个高效的推理引擎,旨在加速模型的部署。本文将介绍如何使用 ONNX Runtime 和相关工具来优化模型的推理速度和资源消耗。
5944 4
|
域名解析 缓存 运维
【域名解析DNS专栏】DNS解析策略:如何实现负载均衡与故障转移
【5月更文挑战第23天】DNS在互联网中扮演关键角色,将域名转换为IP地址。本文探讨DNS的负载均衡和故障转移技术,以增强服务可用性和性能。负载均衡包括轮询(简单分配流量)和加权轮询(按服务器处理能力分配)。故障转移通过主备策略和TTL值实现快速切换,确保服务连续性。实践案例展示了在电商网站如何应用这些策略。DNS策略优化可提升网站速度和稳定性,借助云服务和智能工具,DNS管理更加高效。
1628 1
【域名解析DNS专栏】DNS解析策略:如何实现负载均衡与故障转移
|
Rust 算法 数据安全/隐私保护
【密码学】一文读懂白盒AES(Chow方案)(二)
本文主要参考了文献^[1], 代码参考了^[2], 这里感谢文献作者和代码作者,如果有能力的大佬,可以自行查看原文献,个人水平有限,有哪里写的不对的地方,也欢迎读者指正。
1980 0
【密码学】一文读懂白盒AES(Chow方案)(二)
|
人工智能 自然语言处理 算法
大模型+蒙特卡洛树搜索,一招让LLaMa-3 8B奥数水平直逼GPT-4
【6月更文挑战第25天】 - 复旦大学和上海AI Lab的研究者提出这一算法,用于增强大型语言模型在复杂数学推理任务中的能力,解决现有模型推理准确性问题。 - **MCTSr**流程包括初始化、选择、自细化、自评估、反向传播和UCT更新,通过多轮迭代提升答案质量。 - 实验显示,该算法在**GSM8K**、**GSM Hard**、**MATH**和**Olympiad-level**数据集上表现出色,尤其在多次迭代后。 - 尽管计算成本高且不适用于所有问题类型,但研究揭示了强化LLMs推理能力的新途径,对未来的AI应用具有指导意义。
397 8
技术笔记:tcolorbox宏包简明教程
技术笔记:tcolorbox宏包简明教程
684 0
|
存储 负载均衡 搜索推荐