rand是相当基础的Rust crate,是TRPL中第一个被介绍的非标准库。
本文是粗略的简介,想要详细了解可以看 The Rust Rand Book 以及 https://rust-random.github.io/rand 。
可以通过简单地调用 rand::random() 来获得一个随机值,这是一个泛型函数,需要能够推导出返回类型或者通过 turbo fish 语法显式指定:
1 | let v = rand::random::<(u8, f64)>(); |
更高级的用法涉及到随机数生成器(Random Number Generator, RNG),在 rand 中表示为 Rng trait。这个类型的对象能不断生成一个个随机数。通过对生成的随机数进行一些处理,我们可以获得我们想要性质的随机数序列,比如符合某个随机分布、以某个概率生成随机数等。
大多数情况下rand::thread_rng返回的随机数生成器就够用了。
这里介绍部分 Rng 提供的常用方法:
fn gen<T>(&mut self) -> T生成一个T类型的随机值fn gen_range<T: SampleUniform, B1, B2>(&mut self, low: B1, high: B2) -> T生成区间[low, high)中的随机值,这个特别常用,比如很容易就能生成一个 60 到 100 之间的及格分数:作为对比,在C语言中你得写1
2let mut rng = rand::thread_rng();
let passed_score : u32 = rng.gen_range(60, 101);rand() % (101-60) + 60。fn gen_bool(&mut self, p: f64) -> boolfn gen_ratio(&mut self, numerator: u32, denominator: u32) -> bool这两个函数都是指定概率生成bool值,gen_bool用p指定返回true的概率,gen_ratio返回true的概率被指定为 $\frac{numerator}{denominator}$ 。
rand::seq 封装了关于序列(切片和迭代器)的随机方法。
对切片有 rand::seq::SliceRandom trait,典型方法有:
fn choose<R: ?Sized>(&self, rng: &mut R) -> Option<&Self::Item>随机选择切片中一个元素fn choose_multiple<R: ?Sized>( &self, rng: &mut R, amount: usize ) -> SliceChooseIter<Self, Self::Item>无重复地以随机顺序随机选择切片中amount个元素,返回符合Item=&T的迭代器。fn shuffle<R: ?Sized>(&mut self, rng: &mut R)随机重排整个切片中元素。
对迭代器有 rand::seq::IteratorRandom trait。它的常用方法如下:
fn choose<R: ?Sized>(self, rng: &mut R) -> Option<Self::Item>和SliceRandom::choose类似。fn choose_multiple<R: ?Sized>( self, rng: &mut R, amount: usize ) -> Vec<Self::Item>和SliceRandom::choose_multiple类似,但是返回一个包含了所选元素的Vec,而且不保证其中元素的顺序的随机性,如果需要保证随机顺序,要再shuffle一次。
rand 还有 distribution (概率分布)的相关用法,这里就不说了。