Skip to main content

somatize_study/sampler/
random.rs

1//! Drawn from the space, looking at nothing else.
2
3use super::Sampler;
4use super::drawing::{draw, stream, unit};
5use crate::{Point, Space};
6
7/// Uniform in every knob, independently.
8///
9/// The baseline and not a straw man: over a space where few knobs matter, random
10/// search beats a grid, which spends its budget re-testing the ones that do not
11/// (Bergstra and Bengio, 2012). It is what [`Tpe`](super::Tpe) falls back to
12/// before it has anything to learn from. Its point is a function of the **seed
13/// and the index**, so two machines drawing trial 7 draw the same point.
14#[derive(Debug, Clone, PartialEq, Eq, Hash)]
15pub struct Random {
16    /// The seed. There is no "unseeded": a search you cannot re-run is a result
17    /// you cannot check.
18    pub seed: u64,
19}
20
21impl Random {
22    /// The `trial`-th point. It never runs out, and it never looks at what the
23    /// finished trials did — which is the whole of what it is.
24    pub fn ask(
25        &self,
26        space: &Space,
27        trial: usize,
28        _seen: &[(Point, Option<f64>)],
29    ) -> Option<Point> {
30        if space.is_empty() {
31            return None;
32        }
33        let mut state = stream(self.seed, trial);
34        Some(Point::of(
35            space
36                .dimensions()
37                .iter()
38                .map(|(name, dimension)| (name.clone(), draw(dimension, unit(&mut state))))
39                .collect(),
40        ))
41    }
42}
43
44impl From<Random> for Sampler {
45    fn from(how: Random) -> Self {
46        Self::Random(how)
47    }
48}