How do I create a Vec from a range and shuffle it?
Rand v0.6.0
The Rng::shuffle
method is now deprecated; rand::seq::SliceRandom
trait should be used. It provides the shuffle()
method on all slices, which accepts an Rng
instance:
// Rust edition 2018 no longer needs extern crate
use rand::thread_rng;
use rand::seq::SliceRandom;
fn main() {
let mut vec: Vec<u32> = (0..10).collect();
vec.shuffle(&mut thread_rng());
println!("{:?}", vec);
}
See it on Playground.
Original answer
You're very close. This should work:
extern crate rand;
use rand::{thread_rng, Rng};
fn main() {
let mut vec: Vec<u32> = (0..10).collect();
let slice: &mut [u32] = &mut vec;
thread_rng().shuffle(slice);
}
&mut [T]
is implicitly coercible to &[T]
, and you annotated the slice
variable with &[u32]
, so the slice became immutable: &mut [u32]
was coerced to &[u32]
. mut
on the variable is not relevant here because slices are just borrows into data owned by someone else, so they do not have inherited mutability - their mutability is encoded in their types.
In fact, you don't need an annotation on slice
at all. This works as well:
extern crate rand;
use rand::{thread_rng, Rng};
fn main() {
let mut vec: Vec<u32> = (0..10).collect();
let slice = vec.as_mut_slice();
thread_rng().shuffle(slice);
}
You don't even need the intermediate variable:
extern crate rand;
use rand::{thread_rng, Rng};
fn main() {
let mut vec: Vec<u32> = (0..10).collect();
thread_rng().shuffle(&mut vec);
}
You should read The Rust Programming Language as it explains the concepts of ownership and borrowing and how they interact with mutability.
You can use shuffle
like this:
extern crate rand;
use rand::Rng;
fn main() {
let mut vec: Vec<usize> = (0..10).collect();
println!("{:?}", vec);
rand::thread_rng().shuffle(&mut vec);
println!("{:?}", vec);
}