Merge branch 'shuffle_underflow' into genesis

This commit is contained in:
Paul Hauner
2018-10-22 06:17:02 +11:00
5 changed files with 214 additions and 50 deletions

View File

@@ -25,10 +25,16 @@ pub fn shuffle<T>(
-> Result<Vec<T>, ShuffleErr>
{
let mut rng = ShuffleRng::new(seed);
if list.len() > rng.rand_max as usize {
return Err(ShuffleErr::ExceedsListLength);
}
for i in 0..(list.len() - 1) {
if list.is_empty() {
return Ok(list);
}
for i in 0..(list.len().saturating_sub(1)) {
let n = list.len() - i;
let j = rng.rand_range(n as u32) as usize + i;
list.swap(i, j);
@@ -39,17 +45,40 @@ pub fn shuffle<T>(
#[cfg(test)]
mod tests {
extern crate yaml_rust;
use super::*;
use super::hashing::canonical_hash;
use std::fs::File;
use std::io::prelude::*;
use self::yaml_rust::yaml;
#[test]
fn test_shuffling() {
let seed = canonical_hash(b"4kn4driuctg8");
let list: Vec<usize> = (0..12).collect();
let s = shuffle(&seed, list).unwrap();
assert_eq!(
s,
vec![7, 3, 2, 5, 11, 9, 1, 0, 4, 6, 10, 8],
)
let mut file = File::open("./src/specs/shuffle_test_vectors.yaml").unwrap();
let mut yaml_str = String::new();
file.read_to_string(&mut yaml_str).unwrap();
let docs = yaml::YamlLoader::load_from_str(&yaml_str).unwrap();
let doc = &docs[0];
let test_cases = doc["test_cases"].as_vec();
for test_case in test_cases.unwrap() {
let input = test_case["input"].clone().into_vec().unwrap();
let output = test_case["output"].clone().into_vec().unwrap();
let seed_bytes = test_case["seed"].as_str().unwrap().as_bytes();
let mut seed;
if seed_bytes.len() > 0 {
seed = canonical_hash(seed_bytes);
} else {
seed = vec![];
}
let mut s = shuffle(&seed, input).unwrap();
assert_eq!(s, output);
}
}
}