~ruther/ctu-fee-eoa

9eb722b93f8cc6296d722f68f04e7df86200270d — Rutherther 2 days ago
Initial commit
A  => .envrc +3 -0
@@ 1,3 @@
use guix
SHELL=$(guix shell -m manifest.scm bash-minimal -- bash -c 'echo $GUIX_ENVIRONMENT')
export LD_LIBRARY_PATH=$SHELL/lib

A  => .gitignore +1 -0
@@ 1,1 @@
/target

A  => .project +0 -0
A  => env/.gitignore +1 -0
@@ 1,1 @@
target
\ No newline at end of file

A  => env/Cargo.lock +157 -0
@@ 1,157 @@
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
version = 4

[[package]]
name = "cfg-if"
version = "1.0.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2fd1289c04a9ea8cb22300a459a72a385d7c73d3259e2ed7dcb2af674838cfa9"

[[package]]
name = "env"
version = "0.1.0"
dependencies = [
 "rand",
]

[[package]]
name = "getrandom"
version = "0.3.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "26145e563e54f2cadc477553f1ec5ee650b00862f0a58bcd12cbdc5f0ea2d2f4"
dependencies = [
 "cfg-if",
 "libc",
 "r-efi",
 "wasi",
]

[[package]]
name = "libc"
version = "0.2.176"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "58f929b4d672ea937a23a1ab494143d968337a5f47e56d0815df1e0890ddf174"

[[package]]
name = "ppv-lite86"
version = "0.2.21"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "85eae3c4ed2f50dcfe72643da4befc30deadb458a9b590d720cde2f2b1e97da9"
dependencies = [
 "zerocopy",
]

[[package]]
name = "proc-macro2"
version = "1.0.101"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "89ae43fd86e4158d6db51ad8e2b80f313af9cc74f5c0e03ccb87de09998732de"
dependencies = [
 "unicode-ident",
]

[[package]]
name = "quote"
version = "1.0.41"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ce25767e7b499d1b604768e7cde645d14cc8584231ea6b295e9c9eb22c02e1d1"
dependencies = [
 "proc-macro2",
]

[[package]]
name = "r-efi"
version = "5.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "69cdb34c158ceb288df11e18b4bd39de994f6657d83847bdffdbd7f346754b0f"

[[package]]
name = "rand"
version = "0.9.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6db2770f06117d490610c7488547d543617b21bfa07796d7a12f6f1bd53850d1"
dependencies = [
 "rand_chacha",
 "rand_core",
]

[[package]]
name = "rand_chacha"
version = "0.9.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d3022b5f1df60f26e1ffddd6c66e8aa15de382ae63b3a0c1bfc0e4d3e3f325cb"
dependencies = [
 "ppv-lite86",
 "rand_core",
]

[[package]]
name = "rand_core"
version = "0.9.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "99d9a13982dcf210057a8a78572b2217b667c3beacbf3a0d8b454f6f82837d38"
dependencies = [
 "getrandom",
]

[[package]]
name = "syn"
version = "2.0.106"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ede7c438028d4436d71104916910f5bb611972c5cfd7f89b8300a8186e6fada6"
dependencies = [
 "proc-macro2",
 "quote",
 "unicode-ident",
]

[[package]]
name = "unicode-ident"
version = "1.0.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f63a545481291138910575129486daeaf8ac54aee4387fe7906919f7830c7d9d"

[[package]]
name = "wasi"
version = "0.14.7+wasi-0.2.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "883478de20367e224c0090af9cf5f9fa85bed63a95c1abf3afc5c083ebc06e8c"
dependencies = [
 "wasip2",
]

[[package]]
name = "wasip2"
version = "1.0.1+wasi-0.2.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0562428422c63773dad2c345a1882263bbf4d65cf3f42e90921f787ef5ad58e7"
dependencies = [
 "wit-bindgen",
]

[[package]]
name = "wit-bindgen"
version = "0.46.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f17a85883d4e6d00e8a97c586de764dabcc06133f7f1d55dce5cdc070ad7fe59"

[[package]]
name = "zerocopy"
version = "0.8.27"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0894878a5fa3edfd6da3f88c4805f4c8558e2b996227a3d864f47fe11e38282c"
dependencies = [
 "zerocopy-derive",
]

[[package]]
name = "zerocopy-derive"
version = "0.8.27"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "88d2b8d9c68ad2b9e4340d7832716a4d21a22a1154777ad56ea55c51a9cf3831"
dependencies = [
 "proc-macro2",
 "quote",
 "syn",
]

A  => env/Cargo.toml +7 -0
@@ 1,7 @@
[package]
name = "env"
version = "0.1.0"
edition = "2024"

[dependencies]
rand = "0.9.2"

A  => env/src/main.rs +788 -0
@@ 1,788 @@
use std::{convert::Infallible, fmt::{Binary, Debug}, fs::File, io::{BufRead, BufReader}, marker::PhantomData, num::ParseFloatError, str::FromStr};
use rand::Rng;

fn add(a: u16, b: u16) -> u16 {
    a + b
}

#[derive(Debug, Clone, PartialEq)]
struct BinaryString {
    vec: Vec<i8>
}

struct Bounds {
    min: f64,
    max: f64,
}

impl Bounds {
    pub fn new(min: f64, max: f64) -> Self {
        Bounds {
            min,
            max
        }
    }
}

#[derive(Debug, Clone, PartialEq)]
enum BinaryStringConversionError {
    DimensionMismatch,
    NoBounds
}

impl BinaryString {
    pub fn new(vec: Vec<i8>) -> BinaryString {
        BinaryString {
            vec
        }
    }

    pub fn perturb<TRng>(self: &Self, rng: &mut TRng, p: f64) -> Self
        where TRng : Rng
    {
        BinaryString::new(
            self.into_iter()
                .map(|c| if rng.random::<f64>() <= p { 1 - *c } else { *c })
                .collect::<Vec<i8>>()
        )
    }

    fn to_real_internal<'a, T: DoubleEndedIterator<Item = &'a i8>>(vec: T, len: usize, min: f64, max: f64) -> f64
    {
        let diff = max - min;
        let len = len as i32;
        let max_represent_num = 2f64.powi(len) - 1.0;
        let represented_num = vec
            .rev()
            .enumerate()
            .map(|(bit, c)| diff * (*c as f64) * 2f64.powi(bit as i32))
            .sum::<f64>();

        min + (represented_num / max_represent_num)
    }

    pub fn to_real_single(self: &Self, min: f64, max: f64) -> f64 {
        BinaryString::to_real_internal(self.vec.iter(), self.vec.len(), min, max)
    }

    pub fn to_real(self: &Self, bounds: &Vec<Bounds>) -> Result<Vec<f64>, BinaryStringConversionError> {
        if bounds.len() == 0 {
            return Err(BinaryStringConversionError::NoBounds);
        }

        let chunk_size = self.vec.len() / bounds.len();
        if self.vec.len() % bounds.len() != 0 {
            return Err(BinaryStringConversionError::DimensionMismatch);
        }

        Ok(self.vec.chunks(chunk_size)
            .zip(bounds)
            .map(|(chunk, bound)| BinaryString::to_real_internal(chunk.iter(), chunk_size, bound.min, bound.max))
            .collect::<Vec<f64>>())
    }
}

impl FromStr for BinaryString {
    type Err = String;

    fn from_str(s: &str) -> Result<Self, Self::Err> {
        let binary_vec: Vec<i8> = s
            .chars()
            // skip spaces
            .filter(|c| *c != ' ')
            // Map ones and zeros
            .map(|c| match c {
                '0' => Ok(0),
                '1' => Ok(1),
                _ => Err(format!("Invalid binary character: {}", c)),
            })
            .collect::<Result<Vec<i8>, Self::Err>>()?;

        Ok(BinaryString::new(binary_vec))
    }
}

impl<'a> IntoIterator for &'a BinaryString {
    type Item = &'a i8;
    type IntoIter = std::slice::Iter<'a, i8>;

    fn into_iter(self) -> Self::IntoIter {
        self.vec.iter()
    }
}

trait FittingFunction {
    type In;
    type Out;
    type Err;

    fn fit(self: &Self, inp: &Self::In) -> Result<Self::Out, Self::Err>;
}

// Functions
struct OneMax;
impl OneMax {
    pub fn new() -> Self {
        OneMax
    }
}
impl FittingFunction for OneMax {
    type In = BinaryString;
    type Out = i32;
    type Err = Infallible;

    fn fit(self: &Self, chromosome: &BinaryString) -> Result<i32, Infallible> {
        Ok(chromosome.into_iter()
           .map(|x| *x as i32)
           .sum())
    }
}
struct LABS;

impl LABS {
    fn new() -> Self {
        LABS
    }

    fn Ck(k: usize, S: &Vec<i32>) -> i32 {
        let D = S.len();
        S.iter()
            .take(D - k)
            .zip(S.iter().skip(k))
            .map(|(x, y)| x * y)
            .sum()
    }
}

impl FittingFunction for LABS {
    type In = BinaryString;
    type Out = i32;
    type Err = Infallible;

    fn fit(self: &Self, chromosome: &BinaryString) -> Result<i32, Infallible> {
        let S: Vec<i32> = chromosome
            .into_iter()
            .map(|c| (*c as i32) * 2 - 1)
            .collect();
        let D = S.len();

        Ok((1..=D-1)
           .map(|k| LABS::Ck(k, &S).pow(2))
           .sum())
    }
}

struct Sphere {
    offset: Vec<f64>
}

impl Sphere {
    pub fn new(offset: Vec<f64>) -> Self {
        Sphere {
            offset
        }
    }
}
impl FittingFunction for Sphere {
    type In = Vec<f64>;
    type Out = f64;
    type Err = Infallible;

    fn fit(self: &Self, chromosome: &Vec<f64>) -> Result<f64, Infallible> {
        Ok(chromosome
           .iter()
           .zip(&self.offset)
           .map(|(x, o)| (x - o).powi(2))
           .sum())
    }
}

struct Rosenbrock;

impl Rosenbrock {
    pub fn new() -> Self {
        Rosenbrock
    }
}

impl FittingFunction for Rosenbrock {
    type In = Vec<f64>;
    type Out = f64;
    type Err = Infallible;

    fn fit(self: &Self, inp: &Vec<f64>) -> Result<f64, Infallible> {
        Ok(inp.windows(2)
           .map(|xs| 100.0 * (xs[1] - xs[0].powi(2)).powi(2) + (1.0 - xs[0]).powi(2))
           .sum())
    }
}

struct BinaryFittingWrapper<TFitting> {
    bounds: Vec<Bounds>,
    fitting_function: TFitting,
}

impl<TFitting> BinaryFittingWrapper<TFitting> {
    pub fn new(fitting_function: TFitting, bounds: Vec<Bounds>) -> Self {
        BinaryFittingWrapper {
            fitting_function,
            bounds,
        }
    }
}

impl<TFitting> FittingFunction for BinaryFittingWrapper<TFitting>
where
    TFitting: FittingFunction<In = Vec<f64>, Out = f64, Err = Infallible>
{
    type In = BinaryString;
    type Out = f64;
    type Err = BinaryStringConversionError;

    fn fit(self: &Self, inp: &BinaryString) -> Result<f64, BinaryStringConversionError> {
        Ok(self.fitting_function.fit(&inp.to_real(&self.bounds)?).unwrap())
    }
}

#[derive(Debug, Clone, PartialEq)]
struct LocalSearchCandidate<T>
    where T: Clone
{
    fit: T,
    pos: BinaryString,
    cycle: usize
}

#[derive(Debug, Clone, PartialEq)]
struct LocalSearchResult<T>
    where T: Clone
{
    best_candidate: LocalSearchCandidate<T>,

    // How many cycles there were
    cycles: usize,

    // statistics
    best_candidates: Vec<LocalSearchCandidate<T>>
}

trait TerminatingCondition<T>
    where T: Clone
{
    fn should_terminate(
        self: &mut Self,
        candidate: &LocalSearchCandidate<T>,
        stats: &Vec<LocalSearchCandidate<T>>,
        cycle: usize
    ) -> bool;
}

struct EqualTerminatingCondition {
    target: BinaryString
}

impl EqualTerminatingCondition {
    pub fn new(target: BinaryString) -> Self {
        Self {
            target
        }
    }
}

impl<T: Clone> TerminatingCondition<T> for EqualTerminatingCondition {
    fn should_terminate(
        self: &mut Self,
        candidate: &LocalSearchCandidate<T>,
        _: &Vec<LocalSearchCandidate<T>>,
        _: usize
    ) -> bool {
        candidate.pos == self.target
    }
}

struct NoMatchForTerminatingCondition {
    cycles: usize
}

impl NoMatchForTerminatingCondition {
    pub fn new(cycles: usize) -> Self {
        Self {
            cycles
        }
    }
}

impl<T: Clone> TerminatingCondition<T> for NoMatchForTerminatingCondition {
    fn should_terminate (
        self: &mut Self,
        candidate: &LocalSearchCandidate<T>,
        stats: &Vec<LocalSearchCandidate<T>>,
        cycle: usize
    ) -> bool {
        (cycle - candidate.cycle) > self.cycles
    }
}

trait PerturbationOperator {
    type Chromosome;

    fn perturb(self: &mut Self, chromosome: &Self::Chromosome) -> Self::Chromosome;
}

struct BinaryStringBitPerturbation<TRng: Rng> {
    rng: TRng,
    p: f64,
}

impl BinaryStringBitPerturbation<rand::rngs::ThreadRng> {
    pub fn new(p: f64) -> Self {
        Self {
            rng: rand::rng(),
            p
        }
    }
}

impl<TRng: Rng> PerturbationOperator for BinaryStringBitPerturbation<TRng> {
    type Chromosome = BinaryString;

    fn perturb(self: &mut Self, chromosome: &Self::Chromosome) -> Self::Chromosome {
        chromosome.perturb(&mut self.rng, self.p)
    }
}

trait BetterThanOperator<T> {
    fn better_than(self: &Self, a: &T, b: &T) -> bool;
}

struct DefaultBetterThan;
impl DefaultBetterThan {
    pub fn new() -> Self {
        Self
    }
}

impl<T> BetterThanOperator<T> for DefaultBetterThan
    where T: PartialOrd
{
    fn better_than(self: &Self, a: &T, b: &T) -> bool {
        a < b
    }
}

fn local_search_first_improving<
        T, TErr, TFit, TTerminatingCondition, TPerturbationOperator, TBetterThanOperator>(
    fit: &TFit,
    terminating_condition: &mut TTerminatingCondition,
    perturbation_operator: &mut TPerturbationOperator,
    better_than_operator: &TBetterThanOperator,
    initial: &BinaryString
) -> Result<LocalSearchResult<T>, TErr>
where
    T: Clone,
    TFit: FittingFunction<In = BinaryString, Out = T, Err = TErr>,
    TTerminatingCondition: TerminatingCondition<T>,
    TPerturbationOperator: PerturbationOperator<Chromosome = BinaryString>,
    TBetterThanOperator: BetterThanOperator<T>,
{
    let mut best_candidate = LocalSearchCandidate {
        pos: initial.clone(),
        fit: fit.fit(&initial)?,
        cycle: 0
    };

    let mut stats: Vec<LocalSearchCandidate<T>> = vec![];
    let mut cycle: usize = 0;

    while !terminating_condition.should_terminate(&best_candidate, &stats, cycle) {
        let perturbed = perturbation_operator.perturb(&best_candidate.pos);
        let perturbed_fit = fit.fit(&perturbed)?;

        // Minimize
        if better_than_operator.better_than(&perturbed_fit, &best_candidate.fit) {
            best_candidate = LocalSearchCandidate {
                pos: perturbed.clone(),
                fit: perturbed_fit,
                cycle
            };

            stats.push(best_candidate.clone());
        }

        cycle += 1;
    }

    Ok(LocalSearchResult {
        best_candidate,
        best_candidates: stats,
        cycles: cycle
    })
}

#[test]
fn test_local_search_one_max() {
    let one_max = OneMax::new();
    let optimum = BinaryString::new(vec![0; 10]);

    let result = local_search_first_improving(
        &one_max,
        &mut EqualTerminatingCondition::new(optimum.clone()),
        &mut BinaryStringBitPerturbation::new(0.3),
        &DefaultBetterThan::new(),
        &BinaryString::new(vec![1; 10]),
    ).unwrap();

    println!("{:?}", result);

    assert_eq!(
        result.best_candidate.fit,
        0
    );

    assert_eq!(
        result.best_candidate.pos,
        optimum
    );
}

#[test]
fn test_local_search_sphere() {
    let optimum = BinaryString::new(vec![0, 0, 1, 0, 0,
                                         0, 0, 1, 0, 0]);
    let bounds = vec![Bounds::new(0.0, 31.0), Bounds::new(0.0, 31.0)];
    let optimum_real = optimum.to_real(&bounds).unwrap();
    let sphere = Sphere::new(optimum_real);
    let sphere_wrapped = BinaryFittingWrapper::new(sphere, bounds);

    let result = local_search_first_improving(
        &sphere_wrapped,
        &mut EqualTerminatingCondition::new(optimum.clone()),
        &mut BinaryStringBitPerturbation::new(0.3),
        &DefaultBetterThan::new(),
        &BinaryString::new(vec![1; 10]),
    ).unwrap();

    println!("{:?}", result);

    assert_eq!(
        result.best_candidate.fit,
        0.0
    );

    assert_eq!(
        result.best_candidate.pos,
        optimum
    );
}

#[test]
fn test_perturb() {
    let mut rng = rand::rng();

    assert_eq!(
        BinaryString::new(vec![1, 1, 0, 0])
            .perturb(&mut rng, 1.0)
            .vec,
        vec![0, 0, 1, 1]
    );

    assert_eq!(
        BinaryString::new(vec![1, 1, 0, 0])
            .perturb(&mut rng, 0.0)
            .vec,
        vec![1, 1, 0, 0]
    );
}

#[test]
fn test_binary_string_to_real_single() {
    assert_eq!(
        BinaryString::new(vec![1])
            .to_real_single(0.0, 32.0),
        32.0
    );
    assert_eq!(
        BinaryString::new(vec![1, 1])
            .to_real_single(0.0, 32.0),
        32.0
    );
    assert_eq!(
        BinaryString::new(vec![0, 1])
            .to_real_single(0.0, 32.0),
        32.0 / 3.0
    );
    assert_eq!(
        BinaryString::new(vec![0, 0])
            .to_real_single(-16.0, 16.0),
        -16.0
    );
    assert_eq!(
        BinaryString::new(vec![0, 0, 0, 0, 1])
            .to_real_single(0.0, 31.0),
        1.0
    );
    assert_eq!(
        BinaryString::new(vec![1, 1, 1, 1, 1])
            .to_real_single(0.0, 31.0),
        31.0
    );
    assert_eq!(
        BinaryString::new(vec![0, 0, 0, 1, 0])
            .to_real_single(0.0, 31.0),
        2.0
    );

    assert_eq!(
        BinaryString::new(vec![1; 512])
            .to_real_single(0.0, 31.0),
        31.0
    );
}

#[derive(Debug, Clone, PartialEq)]
struct DataArrOfReals {
    vec: Vec<f64>,
    valid: bool
}

impl FromStr for DataArrOfReals {
    type Err = <f64 as FromStr>::Err;

    fn from_str(s: &str) -> Result<Self, Self::Err> {
        // TODO: maybe better handling, as an error?
        // this would mean also reimplementing load_test_file to be able to supply
        // out the error, but only for the output...
        if !s.starts_with('[') {
            return Ok(
                DataArrOfReals {
                    valid: false,
                    vec: vec![]
                }
            )
        }

        let trimmed = &s[1..s.len()-1];

        Ok(DataArrOfReals {
            valid: true,
            vec: trimmed.split(',')
                .map(|x| x.trim().parse::<f64>())
                .collect::<Result<Vec<f64>, _>>()?
        })
    }
}

fn test_binary_string_to_real(file_name: &str, bounds: Vec<Bounds>) {
    let data = load_test_file::<i8, DataArrOfReals>(file_name);

    for test in data {
        let res = BinaryString::new(test.inp)
                .to_real(&bounds);
        if !test.out.valid {
            assert_eq!(
                res,
                Err(BinaryStringConversionError::DimensionMismatch)
            );
        }
        else {
          assert_eq!(
              res.unwrap(),
              test.out.vec
          );
        }
    }
}

#[test]
fn test_binary_string_to_real_1D_1() {
    test_binary_string_to_real(
        "tests/Bin2Real_1D_1.txt",
        vec![Bounds::new(0.0, 1.0)]
    );
}

#[test]
fn test_binary_string_to_real_1D_2() {
    test_binary_string_to_real(
        "tests/Bin2Real_1D_2.txt",
        vec![Bounds::new(0.0, 4095.0)]
    );
}

#[test]
fn test_binary_string_to_real_1D_3() {
    test_binary_string_to_real(
        "tests/Bin2Real_1D_3.txt",
        vec![Bounds::new(-5.0, 5.0)]
    );
}

#[test]
fn test_binary_string_to_real_2D_1() {
    test_binary_string_to_real(
        "tests/Bin2Real_2D_1.txt",
        vec![Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0)]
    );
}

#[test]
fn test_binary_string_to_real_2D_2() {
    test_binary_string_to_real(
        "tests/Bin2Real_2D_2.txt",
        vec![Bounds::new(0.0, 63.0), Bounds::new(-32.0, 31.0)]
    );
}

#[test]
fn test_binary_string_to_real_2D_3() {
    test_binary_string_to_real(
        "tests/Bin2Real_2D_3.txt",
        vec![Bounds::new(-5.0, 5.0), Bounds::new(0.0, 10.0)]
    );
}

#[test]
fn test_binary_string_to_real_3D_1() {
    test_binary_string_to_real(
        "tests/Bin2Real_3D_1.txt",
        vec![Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0)]
    );
}

#[test]
fn test_binary_string_to_real_3D_2() {
    test_binary_string_to_real(
        "tests/Bin2Real_3D_2.txt",
        vec![Bounds::new(0.0, 15.0), Bounds::new(-8.0, 7.0), Bounds::new(-8.0, 8.0)]
    );
}

#[test]
fn test_binary_string_to_real_4D_1() {
    test_binary_string_to_real(
        "tests/Bin2Real_4D_1.txt",
        vec![Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0)]
    );
}

#[test]
fn test_binary_string_to_real_4D_2() {
    test_binary_string_to_real(
        "tests/Bin2Real_4D_2.txt",
        vec![Bounds::new(0.0, 7.0), Bounds::new(-4.0, 3.0), Bounds::new(-4.0, 4.0), Bounds::new(-8.0, 0.0)]
    );
}

#[test]
fn test_binary_string_to_real_6D_1() {
    test_binary_string_to_real(
        "tests/Bin2Real_6D_1.txt",
        vec![Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0), Bounds::new(0.0, 1.0)]
    );
}

#[test]
fn test_binary_string_to_real_6D_2() {
    test_binary_string_to_real(
        "tests/Bin2Real_6D_2.txt",
        (0..=5).map(|x| Bounds::new(x as f64, (2 * (x + 1)) as f64)).collect::<Vec<_>>()
    );
}

#[test]
fn test_one_max() {
    let data = load_test_file::<i8, i32>("tests/onemax.txt");

    for test in data {
        assert_eq!(
            OneMax::new().fit(&BinaryString::new(test.inp)).unwrap(),
            test.out
        );
    }
}

#[test]
fn test_LABS() {
    let data = load_test_file::<i8, i32>("tests/labs.txt");

    for test in data {
        println!("Test vector {}", test.inp.iter()
            .map(|x| x.to_string())
            .collect::<Vec<String>>()
            .join(", "));
        assert_eq!(
            LABS::new().fit(&BinaryString::new(test.inp)).unwrap(),
            test.out
        )
     }
}

#[test]
fn test_sphere() {
    let data = load_test_file::<f64, f64>("tests/sphere.txt");

    for test in data {
        assert_eq!(
            Sphere::new(vec![1.0; 10]).fit(&test.inp).unwrap(),
            test.out
        )
    }
}

#[test]
fn test_rosenbrock() {
    let data = load_test_file::<f64, f64>("tests/rosenbrock.txt");

    for test in data {
        assert_eq!(
            Rosenbrock::new().fit(&test.inp).unwrap(),
            test.out
        )
    }
}

// Test infra
struct TestVector<TIn, TOut> {
    inp: Vec<TIn>,
    out: TOut
}

fn load_test_file<TIn, TOut>(file: &str) -> Vec<TestVector::<TIn, TOut>>
where
  TIn : FromStr + Debug,
  TIn::Err: Debug,
  TOut : FromStr + Debug,
  TOut::Err: Debug,
{
    let mut vectors: Vec<TestVector::<TIn, TOut>> = vec![];

    let file = File::open(file).expect("Could not read test data!");
    let reader = BufReader::new(file);

    for (_, line) in reader.lines().enumerate() {
        let line = line.expect("Could not read a line!");

        if line.starts_with('#') || line.len() == 0 {
            continue;
        }

        let (inp_str, out_str) = line.split_once(":").unwrap();

        let out: TOut = out_str.trim().parse::<TOut>().unwrap();
        let inp: Vec<TIn> = inp_str.split(' ')
            .filter(|num| num.len() > 0)
            .map(|num| num.trim().parse().unwrap())
            .collect();

        vectors.push(TestVector::<TIn, TOut> {
            inp,
            out
        });
    }

    vectors
}

fn main() {
    println!("Hello, world! {}", add(1, 2));
}

A  => env/tests/Bin2Real_1D_1.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 1D, interval (0, 1)
0 : [0.0]
1 : [1.0]
0 0 : [0.0]
0 1 : [0.3333333333333333]
1 0 : [0.6666666666666666]
1 1 : [1.0]
0 0 0 : [0.0]
0 0 1 : [0.14285714285714285]
0 1 0 : [0.2857142857142857]
0 1 1 : [0.42857142857142855]
1 0 0 : [0.5714285714285714]
1 0 1 : [0.7142857142857143]
1 1 0 : [0.8571428571428571]
1 1 1 : [1.0]
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [1.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [0.0002442002442002442]
0 1 1 1 1 1 1 1 1 1 1 1 : [0.4998778998778999]
1 0 0 0 0 0 0 0 0 0 0 0 : [0.5001221001221001]
1 1 1 1 1 1 1 1 1 1 1 0 : [0.9997557997557998]
0 0 0 0 0 1 0 0 0 0 0 1 : [0.015873015873015872]
0 1 1 1 1 1 0 1 1 1 1 1 : [0.49206349206349204]
1 0 0 0 0 0 1 0 0 0 0 0 : [0.5079365079365079]
1 1 1 1 1 0 1 1 1 1 1 0 : [0.9841269841269841]
0 0 0 1 0 0 0 1 0 0 0 1 : [0.06666666666666667]
0 1 1 1 0 1 1 1 0 1 1 1 : [0.4666666666666667]
1 0 0 0 1 0 0 0 1 0 0 0 : [0.5333333333333333]
1 1 1 0 1 1 1 0 1 1 1 0 : [0.9333333333333333]
0 0 1 0 0 1 0 0 1 0 0 1 : [0.14285714285714285]
0 1 1 0 1 1 0 1 1 0 1 1 : [0.42857142857142855]
1 0 0 1 0 0 1 0 0 1 0 0 : [0.5714285714285714]
1 1 0 1 1 0 1 1 0 1 1 0 : [0.8571428571428571]
0 1 0 1 0 1 0 1 0 1 0 1 : [0.3333333333333333]
1 0 1 0 1 0 1 0 1 0 1 0 : [0.6666666666666666]

A  => env/tests/Bin2Real_1D_2.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 1D, interval (0, 4095)
0 : [0.0]
1 : [4095.0]
0 0 : [0.0]
0 1 : [1365.0]
1 0 : [2730.0]
1 1 : [4095.0]
0 0 0 : [0.0]
0 0 1 : [585.0]
0 1 0 : [1170.0]
0 1 1 : [1755.0]
1 0 0 : [2340.0]
1 0 1 : [2925.0]
1 1 0 : [3510.0]
1 1 1 : [4095.0]
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [4095.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [1.0]
0 1 1 1 1 1 1 1 1 1 1 1 : [2047.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [2048.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [4094.0]
0 0 0 0 0 1 0 0 0 0 0 1 : [65.0]
0 1 1 1 1 1 0 1 1 1 1 1 : [2015.0]
1 0 0 0 0 0 1 0 0 0 0 0 : [2080.0]
1 1 1 1 1 0 1 1 1 1 1 0 : [4030.0]
0 0 0 1 0 0 0 1 0 0 0 1 : [273.0]
0 1 1 1 0 1 1 1 0 1 1 1 : [1911.0]
1 0 0 0 1 0 0 0 1 0 0 0 : [2184.0]
1 1 1 0 1 1 1 0 1 1 1 0 : [3822.0]
0 0 1 0 0 1 0 0 1 0 0 1 : [585.0]
0 1 1 0 1 1 0 1 1 0 1 1 : [1755.0]
1 0 0 1 0 0 1 0 0 1 0 0 : [2340.0]
1 1 0 1 1 0 1 1 0 1 1 0 : [3510.0]
0 1 0 1 0 1 0 1 0 1 0 1 : [1365.0]
1 0 1 0 1 0 1 0 1 0 1 0 : [2730.0]

A  => env/tests/Bin2Real_1D_3.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 1D, interval (-5, 5)
0 : [-5.0]
1 : [5.0]
0 0 : [-5.0]
0 1 : [-1.6666666666666665]
1 0 : [1.666666666666667]
1 1 : [5.0]
0 0 0 : [-5.0]
0 0 1 : [-3.571428571428571]
0 1 0 : [-2.142857142857143]
0 1 1 : [-0.7142857142857144]
1 0 0 : [0.7142857142857144]
1 0 1 : [2.1428571428571432]
1 1 0 : [3.571428571428571]
1 1 1 : [5.0]
0 0 0 0 0 0 0 0 0 0 0 0 : [-5.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [5.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [-4.997557997557998]
0 1 1 1 1 1 1 1 1 1 1 1 : [-0.0012210012210012167]
1 0 0 0 0 0 0 0 0 0 0 0 : [0.0012210012210012167]
1 1 1 1 1 1 1 1 1 1 1 0 : [4.997557997557998]
0 0 0 0 0 1 0 0 0 0 0 1 : [-4.841269841269841]
0 1 1 1 1 1 0 1 1 1 1 1 : [-0.07936507936507908]
1 0 0 0 0 0 1 0 0 0 0 0 : [0.07936507936507908]
1 1 1 1 1 0 1 1 1 1 1 0 : [4.841269841269842]
0 0 0 1 0 0 0 1 0 0 0 1 : [-4.333333333333333]
0 1 1 1 0 1 1 1 0 1 1 1 : [-0.33333333333333304]
1 0 0 0 1 0 0 0 1 0 0 0 : [0.33333333333333304]
1 1 1 0 1 1 1 0 1 1 1 0 : [4.333333333333334]
0 0 1 0 0 1 0 0 1 0 0 1 : [-3.571428571428571]
0 1 1 0 1 1 0 1 1 0 1 1 : [-0.7142857142857144]
1 0 0 1 0 0 1 0 0 1 0 0 : [0.7142857142857144]
1 1 0 1 1 0 1 1 0 1 1 0 : [3.571428571428571]
0 1 0 1 0 1 0 1 0 1 0 1 : [-1.6666666666666665]
1 0 1 0 1 0 1 0 1 0 1 0 : [1.666666666666667]

A  => env/tests/Bin2Real_2D_1.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 2D, interval from (0,0) to (1,1)
0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 : [0.0, 0.0]
0 1 : [0.0, 1.0]
1 0 : [1.0, 0.0]
1 1 : [1.0, 1.0]
0 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0, 0.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [1.0, 1.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [0.0, 0.015873015873015872]
0 1 1 1 1 1 1 1 1 1 1 1 : [0.49206349206349204, 1.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [0.5079365079365079, 0.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [1.0, 0.9841269841269841]
0 0 0 0 0 1 0 0 0 0 0 1 : [0.015873015873015872, 0.015873015873015872]
0 1 1 1 1 1 0 1 1 1 1 1 : [0.49206349206349204, 0.49206349206349204]
1 0 0 0 0 0 1 0 0 0 0 0 : [0.5079365079365079, 0.5079365079365079]
1 1 1 1 1 0 1 1 1 1 1 0 : [0.9841269841269841, 0.9841269841269841]
0 0 0 1 0 0 0 1 0 0 0 1 : [0.06349206349206349, 0.2698412698412698]
0 1 1 1 0 1 1 1 0 1 1 1 : [0.4603174603174603, 0.873015873015873]
1 0 0 0 1 0 0 0 1 0 0 0 : [0.5396825396825397, 0.12698412698412698]
1 1 1 0 1 1 1 0 1 1 1 0 : [0.9365079365079365, 0.7301587301587301]
0 0 1 0 0 1 0 0 1 0 0 1 : [0.14285714285714285, 0.14285714285714285]
0 1 1 0 1 1 0 1 1 0 1 1 : [0.42857142857142855, 0.42857142857142855]
1 0 0 1 0 0 1 0 0 1 0 0 : [0.5714285714285714, 0.5714285714285714]
1 1 0 1 1 0 1 1 0 1 1 0 : [0.8571428571428571, 0.8571428571428571]
0 1 0 1 0 1 0 1 0 1 0 1 : [0.3333333333333333, 0.3333333333333333]
1 0 1 0 1 0 1 0 1 0 1 0 : [0.6666666666666666, 0.6666666666666666]

A  => env/tests/Bin2Real_2D_2.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 2D, interval from (0,-32) to (63,31)
0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 : [0.0, -32.0]
0 1 : [0.0, 31.0]
1 0 : [63.0, -32.0]
1 1 : [63.0, 31.0]
0 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0, -32.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [63.0, 31.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [0.0, -31.0]
0 1 1 1 1 1 1 1 1 1 1 1 : [31.0, 31.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [32.0, -32.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [63.0, 30.0]
0 0 0 0 0 1 0 0 0 0 0 1 : [1.0, -31.0]
0 1 1 1 1 1 0 1 1 1 1 1 : [31.0, -1.0]
1 0 0 0 0 0 1 0 0 0 0 0 : [32.0, 0.0]
1 1 1 1 1 0 1 1 1 1 1 0 : [62.0, 30.0]
0 0 0 1 0 0 0 1 0 0 0 1 : [4.0, -15.0]
0 1 1 1 0 1 1 1 0 1 1 1 : [29.0, 23.0]
1 0 0 0 1 0 0 0 1 0 0 0 : [34.0, -24.0]
1 1 1 0 1 1 1 0 1 1 1 0 : [59.0, 14.0]
0 0 1 0 0 1 0 0 1 0 0 1 : [9.0, -23.0]
0 1 1 0 1 1 0 1 1 0 1 1 : [27.0, -5.0]
1 0 0 1 0 0 1 0 0 1 0 0 : [36.0, 4.0]
1 1 0 1 1 0 1 1 0 1 1 0 : [54.0, 22.0]
0 1 0 1 0 1 0 1 0 1 0 1 : [21.0, -11.0]
1 0 1 0 1 0 1 0 1 0 1 0 : [42.0, 10.0]

A  => env/tests/Bin2Real_2D_3.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 2D, interval from (-5,0) to (5,10)
0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 : [-5.0, 0.0]
0 1 : [-5.0, 10.0]
1 0 : [5.0, 0.0]
1 1 : [5.0, 10.0]
0 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 0 0 0 0 0 0 0 0 0 : [-5.0, 0.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [5.0, 10.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [-5.0, 0.15873015873015872]
0 1 1 1 1 1 1 1 1 1 1 1 : [-0.07936507936507908, 10.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [0.07936507936507908, 0.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [5.0, 9.841269841269842]
0 0 0 0 0 1 0 0 0 0 0 1 : [-4.841269841269841, 0.15873015873015872]
0 1 1 1 1 1 0 1 1 1 1 1 : [-0.07936507936507908, 4.920634920634921]
1 0 0 0 0 0 1 0 0 0 0 0 : [0.07936507936507908, 5.079365079365079]
1 1 1 1 1 0 1 1 1 1 1 0 : [4.841269841269842, 9.841269841269842]
0 0 0 1 0 0 0 1 0 0 0 1 : [-4.365079365079366, 2.6984126984126986]
0 1 1 1 0 1 1 1 0 1 1 1 : [-0.3968253968253972, 8.73015873015873]
1 0 0 0 1 0 0 0 1 0 0 0 : [0.3968253968253972, 1.2698412698412698]
1 1 1 0 1 1 1 0 1 1 1 0 : [4.365079365079366, 7.301587301587301]
0 0 1 0 0 1 0 0 1 0 0 1 : [-3.571428571428571, 1.4285714285714286]
0 1 1 0 1 1 0 1 1 0 1 1 : [-0.7142857142857144, 4.285714285714286]
1 0 0 1 0 0 1 0 0 1 0 0 : [0.7142857142857144, 5.714285714285714]
1 1 0 1 1 0 1 1 0 1 1 0 : [3.571428571428571, 8.571428571428571]
0 1 0 1 0 1 0 1 0 1 0 1 : [-1.6666666666666665, 3.3333333333333335]
1 0 1 0 1 0 1 0 1 0 1 0 : [1.666666666666667, 6.666666666666667]

A  => env/tests/Bin2Real_3D_1.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 2D, interval from (0,0,0) to (1,1,1)
0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 : [0.0, 0.0, 0.0]
0 0 1 : [0.0, 0.0, 1.0]
0 1 0 : [0.0, 1.0, 0.0]
0 1 1 : [0.0, 1.0, 1.0]
1 0 0 : [1.0, 0.0, 0.0]
1 0 1 : [1.0, 0.0, 1.0]
1 1 0 : [1.0, 1.0, 0.0]
1 1 1 : [1.0, 1.0, 1.0]
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0, 0.0, 0.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [1.0, 1.0, 1.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [0.0, 0.0, 0.06666666666666667]
0 1 1 1 1 1 1 1 1 1 1 1 : [0.4666666666666667, 1.0, 1.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [0.5333333333333333, 0.0, 0.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [1.0, 1.0, 0.9333333333333333]
0 0 0 0 0 1 0 0 0 0 0 1 : [0.0, 0.26666666666666666, 0.06666666666666667]
0 1 1 1 1 1 0 1 1 1 1 1 : [0.4666666666666667, 0.8666666666666667, 1.0]
1 0 0 0 0 0 1 0 0 0 0 0 : [0.5333333333333333, 0.13333333333333333, 0.0]
1 1 1 1 1 0 1 1 1 1 1 0 : [1.0, 0.7333333333333333, 0.9333333333333333]
0 0 0 1 0 0 0 1 0 0 0 1 : [0.06666666666666667, 0.06666666666666667, 0.06666666666666667]
0 1 1 1 0 1 1 1 0 1 1 1 : [0.4666666666666667, 0.4666666666666667, 0.4666666666666667]
1 0 0 0 1 0 0 0 1 0 0 0 : [0.5333333333333333, 0.5333333333333333, 0.5333333333333333]
1 1 1 0 1 1 1 0 1 1 1 0 : [0.9333333333333333, 0.9333333333333333, 0.9333333333333333]
0 0 1 0 0 1 0 0 1 0 0 1 : [0.13333333333333333, 0.26666666666666666, 0.6]
0 1 1 0 1 1 0 1 1 0 1 1 : [0.4, 0.8666666666666667, 0.7333333333333333]
1 0 0 1 0 0 1 0 0 1 0 0 : [0.6, 0.13333333333333333, 0.26666666666666666]
1 1 0 1 1 0 1 1 0 1 1 0 : [0.8666666666666667, 0.7333333333333333, 0.4]
0 1 0 1 0 1 0 1 0 1 0 1 : [0.3333333333333333, 0.3333333333333333, 0.3333333333333333]
1 0 1 0 1 0 1 0 1 0 1 0 : [0.6666666666666666, 0.6666666666666666, 0.6666666666666666]

A  => env/tests/Bin2Real_3D_2.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 2D, interval from (0,-8,-8) to (15,7,8)
0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 : [0.0, -8.0, -8.0]
0 0 1 : [0.0, -8.0, 8.0]
0 1 0 : [0.0, 7.0, -8.0]
0 1 1 : [0.0, 7.0, 8.0]
1 0 0 : [15.0, -8.0, -8.0]
1 0 1 : [15.0, -8.0, 8.0]
1 1 0 : [15.0, 7.0, -8.0]
1 1 1 : [15.0, 7.0, 8.0]
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0, -8.0, -8.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [15.0, 7.0, 8.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [0.0, -8.0, -6.933333333333334]
0 1 1 1 1 1 1 1 1 1 1 1 : [7.0, 7.0, 8.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [8.0, -8.0, -8.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [15.0, 7.0, 6.933333333333334]
0 0 0 0 0 1 0 0 0 0 0 1 : [0.0, -4.0, -6.933333333333334]
0 1 1 1 1 1 0 1 1 1 1 1 : [7.0, 5.0, 8.0]
1 0 0 0 0 0 1 0 0 0 0 0 : [8.0, -6.0, -8.0]
1 1 1 1 1 0 1 1 1 1 1 0 : [15.0, 3.0, 6.933333333333334]
0 0 0 1 0 0 0 1 0 0 0 1 : [1.0, -7.0, -6.933333333333334]
0 1 1 1 0 1 1 1 0 1 1 1 : [7.0, -1.0, -0.5333333333333332]
1 0 0 0 1 0 0 0 1 0 0 0 : [8.0, 0.0, 0.5333333333333332]
1 1 1 0 1 1 1 0 1 1 1 0 : [14.0, 6.0, 6.933333333333334]
0 0 1 0 0 1 0 0 1 0 0 1 : [2.0, -4.0, 1.5999999999999996]
0 1 1 0 1 1 0 1 1 0 1 1 : [6.0, 5.0, 3.7333333333333325]
1 0 0 1 0 0 1 0 0 1 0 0 : [9.0, -6.0, -3.7333333333333334]
1 1 0 1 1 0 1 1 0 1 1 0 : [13.0, 3.0, -1.5999999999999996]
0 1 0 1 0 1 0 1 0 1 0 1 : [5.0, -3.0, -2.666666666666667]
1 0 1 0 1 0 1 0 1 0 1 0 : [10.0, 2.0, 2.666666666666666]

A  => env/tests/Bin2Real_4D_1.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 2D, interval from (0,0,0,0) to (1,1,1,1)
0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0, 0.0, 0.0, 0.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [1.0, 1.0, 1.0, 1.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [0.0, 0.0, 0.0, 0.14285714285714285]
0 1 1 1 1 1 1 1 1 1 1 1 : [0.42857142857142855, 1.0, 1.0, 1.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [0.5714285714285714, 0.0, 0.0, 0.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [1.0, 1.0, 1.0, 0.8571428571428571]
0 0 0 0 0 1 0 0 0 0 0 1 : [0.0, 0.14285714285714285, 0.0, 0.14285714285714285]
0 1 1 1 1 1 0 1 1 1 1 1 : [0.42857142857142855, 1.0, 0.42857142857142855, 1.0]
1 0 0 0 0 0 1 0 0 0 0 0 : [0.5714285714285714, 0.0, 0.5714285714285714, 0.0]
1 1 1 1 1 0 1 1 1 1 1 0 : [1.0, 0.8571428571428571, 1.0, 0.8571428571428571]
0 0 0 1 0 0 0 1 0 0 0 1 : [0.0, 0.5714285714285714, 0.2857142857142857, 0.14285714285714285]
0 1 1 1 0 1 1 1 0 1 1 1 : [0.42857142857142855, 0.7142857142857143, 0.8571428571428571, 1.0]
1 0 0 0 1 0 0 0 1 0 0 0 : [0.5714285714285714, 0.2857142857142857, 0.14285714285714285, 0.0]
1 1 1 0 1 1 1 0 1 1 1 0 : [1.0, 0.42857142857142855, 0.7142857142857143, 0.8571428571428571]
0 0 1 0 0 1 0 0 1 0 0 1 : [0.14285714285714285, 0.14285714285714285, 0.14285714285714285, 0.14285714285714285]
0 1 1 0 1 1 0 1 1 0 1 1 : [0.42857142857142855, 0.42857142857142855, 0.42857142857142855, 0.42857142857142855]
1 0 0 1 0 0 1 0 0 1 0 0 : [0.5714285714285714, 0.5714285714285714, 0.5714285714285714, 0.5714285714285714]
1 1 0 1 1 0 1 1 0 1 1 0 : [0.8571428571428571, 0.8571428571428571, 0.8571428571428571, 0.8571428571428571]
0 1 0 1 0 1 0 1 0 1 0 1 : [0.2857142857142857, 0.7142857142857143, 0.2857142857142857, 0.7142857142857143]
1 0 1 0 1 0 1 0 1 0 1 0 : [0.7142857142857143, 0.2857142857142857, 0.7142857142857143, 0.2857142857142857]

A  => env/tests/Bin2Real_4D_2.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 2D, interval from (0,-4,-4,-8) to (7,3,4,0)
0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0, -4.0, -4.0, -8.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [7.0, 3.0, 4.0, 0.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [0.0, -4.0, -4.0, -6.857142857142858]
0 1 1 1 1 1 1 1 1 1 1 1 : [3.0, 3.0, 4.0, 0.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [4.0, -4.0, -4.0, -8.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [7.0, 3.0, 4.0, -1.1428571428571432]
0 0 0 0 0 1 0 0 0 0 0 1 : [0.0, -3.0, -4.0, -6.857142857142858]
0 1 1 1 1 1 0 1 1 1 1 1 : [3.0, 3.0, -0.5714285714285716, 0.0]
1 0 0 0 0 0 1 0 0 0 0 0 : [4.0, -4.0, 0.5714285714285712, -8.0]
1 1 1 1 1 0 1 1 1 1 1 0 : [7.0, 2.0, 4.0, -1.1428571428571432]
0 0 0 1 0 0 0 1 0 0 0 1 : [0.0, 0.0, -1.7142857142857144, -6.857142857142858]
0 1 1 1 0 1 1 1 0 1 1 1 : [3.0, 1.0, 2.8571428571428568, 0.0]
1 0 0 0 1 0 0 0 1 0 0 0 : [4.0, -2.0, -2.857142857142857, -8.0]
1 1 1 0 1 1 1 0 1 1 1 0 : [7.0, -1.0, 1.7142857142857144, -1.1428571428571432]
0 0 1 0 0 1 0 0 1 0 0 1 : [1.0, -3.0, -2.857142857142857, -6.857142857142858]
0 1 1 0 1 1 0 1 1 0 1 1 : [3.0, -1.0, -0.5714285714285716, -4.571428571428571]
1 0 0 1 0 0 1 0 0 1 0 0 : [4.0, 0.0, 0.5714285714285712, -3.428571428571429]
1 1 0 1 1 0 1 1 0 1 1 0 : [6.0, 2.0, 2.8571428571428568, -1.1428571428571432]
0 1 0 1 0 1 0 1 0 1 0 1 : [2.0, 1.0, -1.7142857142857144, -2.2857142857142856]
1 0 1 0 1 0 1 0 1 0 1 0 : [5.0, -2.0, 1.7142857142857144, -5.714285714285714]

A  => env/tests/Bin2Real_6D_1.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 2D, interval from (0,0,0,0,0,0) to (1,1,1,1,1,1)
0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0, 0.0, 0.0, 0.0, 0.0, 0.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [1.0, 1.0, 1.0, 1.0, 1.0, 1.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [0.0, 0.0, 0.0, 0.0, 0.0, 0.3333333333333333]
0 1 1 1 1 1 1 1 1 1 1 1 : [0.3333333333333333, 1.0, 1.0, 1.0, 1.0, 1.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [0.6666666666666666, 0.0, 0.0, 0.0, 0.0, 0.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [1.0, 1.0, 1.0, 1.0, 1.0, 0.6666666666666666]
0 0 0 0 0 1 0 0 0 0 0 1 : [0.0, 0.0, 0.3333333333333333, 0.0, 0.0, 0.3333333333333333]
0 1 1 1 1 1 0 1 1 1 1 1 : [0.3333333333333333, 1.0, 1.0, 0.3333333333333333, 1.0, 1.0]
1 0 0 0 0 0 1 0 0 0 0 0 : [0.6666666666666666, 0.0, 0.0, 0.6666666666666666, 0.0, 0.0]
1 1 1 1 1 0 1 1 1 1 1 0 : [1.0, 1.0, 0.6666666666666666, 1.0, 1.0, 0.6666666666666666]
0 0 0 1 0 0 0 1 0 0 0 1 : [0.0, 0.3333333333333333, 0.0, 0.3333333333333333, 0.0, 0.3333333333333333]
0 1 1 1 0 1 1 1 0 1 1 1 : [0.3333333333333333, 1.0, 0.3333333333333333, 1.0, 0.3333333333333333, 1.0]
1 0 0 0 1 0 0 0 1 0 0 0 : [0.6666666666666666, 0.0, 0.6666666666666666, 0.0, 0.6666666666666666, 0.0]
1 1 1 0 1 1 1 0 1 1 1 0 : [1.0, 0.6666666666666666, 1.0, 0.6666666666666666, 1.0, 0.6666666666666666]
0 0 1 0 0 1 0 0 1 0 0 1 : [0.0, 0.6666666666666666, 0.3333333333333333, 0.0, 0.6666666666666666, 0.3333333333333333]
0 1 1 0 1 1 0 1 1 0 1 1 : [0.3333333333333333, 0.6666666666666666, 1.0, 0.3333333333333333, 0.6666666666666666, 1.0]
1 0 0 1 0 0 1 0 0 1 0 0 : [0.6666666666666666, 0.3333333333333333, 0.0, 0.6666666666666666, 0.3333333333333333, 0.0]
1 1 0 1 1 0 1 1 0 1 1 0 : [1.0, 0.3333333333333333, 0.6666666666666666, 1.0, 0.3333333333333333, 0.6666666666666666]
0 1 0 1 0 1 0 1 0 1 0 1 : [0.3333333333333333, 0.3333333333333333, 0.3333333333333333, 0.3333333333333333, 0.3333333333333333, 0.3333333333333333]
1 0 1 0 1 0 1 0 1 0 1 0 : [0.6666666666666666, 0.6666666666666666, 0.6666666666666666, 0.6666666666666666, 0.6666666666666666, 0.6666666666666666]

A  => env/tests/Bin2Real_6D_2.txt +35 -0
@@ 1,35 @@
# Binary to real test data, 2D, interval from (0,1,2,3,4,5) to (2,4,6,8,10,12)
0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 0 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 0 : The binary vector length is not divisible by the dimensionality of the target vector space.
1 1 1 : The binary vector length is not divisible by the dimensionality of the target vector space.
0 0 0 0 0 0 0 0 0 0 0 0 : [0.0, 1.0, 2.0, 3.0, 4.0, 5.0]
1 1 1 1 1 1 1 1 1 1 1 1 : [2.0, 4.0, 6.0, 8.0, 10.0, 12.0]
0 0 0 0 0 0 0 0 0 0 0 1 : [0.0, 1.0, 2.0, 3.0, 4.0, 7.333333333333334]
0 1 1 1 1 1 1 1 1 1 1 1 : [0.6666666666666666, 4.0, 6.0, 8.0, 10.0, 12.0]
1 0 0 0 0 0 0 0 0 0 0 0 : [1.3333333333333333, 1.0, 2.0, 3.0, 4.0, 5.0]
1 1 1 1 1 1 1 1 1 1 1 0 : [2.0, 4.0, 6.0, 8.0, 10.0, 9.666666666666668]
0 0 0 0 0 1 0 0 0 0 0 1 : [0.0, 1.0, 3.333333333333333, 3.0, 4.0, 7.333333333333334]
0 1 1 1 1 1 0 1 1 1 1 1 : [0.6666666666666666, 4.0, 6.0, 4.666666666666667, 10.0, 12.0]
1 0 0 0 0 0 1 0 0 0 0 0 : [1.3333333333333333, 1.0, 2.0, 6.333333333333334, 4.0, 5.0]
1 1 1 1 1 0 1 1 1 1 1 0 : [2.0, 4.0, 4.666666666666666, 8.0, 10.0, 9.666666666666668]
0 0 0 1 0 0 0 1 0 0 0 1 : [0.0, 2.0, 2.0, 4.666666666666667, 4.0, 7.333333333333334]
0 1 1 1 0 1 1 1 0 1 1 1 : [0.6666666666666666, 4.0, 3.333333333333333, 8.0, 6.0, 12.0]
1 0 0 0 1 0 0 0 1 0 0 0 : [1.3333333333333333, 1.0, 4.666666666666666, 3.0, 8.0, 5.0]
1 1 1 0 1 1 1 0 1 1 1 0 : [2.0, 3.0, 6.0, 6.333333333333334, 10.0, 9.666666666666668]
0 0 1 0 0 1 0 0 1 0 0 1 : [0.0, 3.0, 3.333333333333333, 3.0, 8.0, 7.333333333333334]
0 1 1 0 1 1 0 1 1 0 1 1 : [0.6666666666666666, 3.0, 6.0, 4.666666666666667, 8.0, 12.0]
1 0 0 1 0 0 1 0 0 1 0 0 : [1.3333333333333333, 2.0, 2.0, 6.333333333333334, 6.0, 5.0]
1 1 0 1 1 0 1 1 0 1 1 0 : [2.0, 2.0, 4.666666666666666, 8.0, 6.0, 9.666666666666668]
0 1 0 1 0 1 0 1 0 1 0 1 : [0.6666666666666666, 2.0, 3.333333333333333, 4.666666666666667, 6.0, 7.333333333333334]
1 0 1 0 1 0 1 0 1 0 1 0 : [1.3333333333333333, 3.0, 4.666666666666666, 6.333333333333334, 8.0, 9.666666666666668]

A  => env/tests/labs.txt +22 -0
@@ 1,22 @@
# Test data for LABS function
0 : 0
1 : 0
0 0 : 1
0 1 : 1
1 0 : 1
1 1 : 1
0 0 0 : 5
0 0 1 : 1
0 1 0 : 5
0 1 1 : 1
1 0 0 : 1
1 0 1 : 5
1 1 0 : 1
1 1 1 : 5
0 0 0 0 0 0 0 0 0 0 : 285
0 1 0 1 0 1 0 1 0 1 : 285
0 0 1 1 0 0 1 1 0 0 : 125
1 1 0 0 1 1 0 0 1 1 : 125
0 0 0 0 0 1 1 1 1 1 : 125
1 1 1 1 1 0 0 0 0 0 : 125
1 1 1 1 1 1 1 1 1 1 : 285

A  => env/tests/onemax.txt +22 -0
@@ 1,22 @@
# Test data for OneMax function
0 : 0
1 : 1
0 0 : 0
0 1 : 1
1 0 : 1
1 1 : 2
0 0 0 : 0
0 0 1 : 1
0 1 0 : 1
0 1 1 : 2
1 0 0 : 1
1 0 1 : 2
1 1 0 : 2
1 1 1 : 3
0 0 0 0 0 0 0 0 0 0 : 0
0 1 0 1 0 1 0 1 0 1 : 5
0 0 1 1 0 0 1 1 0 0 : 4
1 1 0 0 1 1 0 0 1 1 : 6
0 0 0 0 0 1 1 1 1 1 : 5
1 1 1 1 1 0 0 0 0 0 : 5
1 1 1 1 1 1 1 1 1 1 : 10

A  => env/tests/rosenbrock.txt +32 -0
@@ 1,32 @@
# Test data for Rosenbrock function. Function is not defined for 1D vectors; here it produces 0. 
0 : 0
0.5 : 0
1 : 0
-0.5 : 0
-5 : 0
5 : 0
0 0 : 1
-1 -1 : 404
-1 1 : 4
1 -1 : 400
1 1 : 0
-0.1 -0.2 : 5.620000000000001
0.1 0.2 : 4.42
-5 -5 : 90036
-5 5 : 40036
5 -5 : 90016
5 5 : 40016
0 0 0 : 2
1 1 1 : 0
-5 -5 -5 : 180072
-5 -5 5 : 130072
-5 5 -5 : 130052
-5 5 5 : 80052
5 -5 -5 : 180052
5 -5 5 : 130052
5 5 -5 : 130032
5 5 5 : 80032
-0.1 -1.2 -2.3 -3.4 -4.5 -5.6 -6.7 -7.8 -8.9 -9.1 : 1790768.58
0.1 1.2 2.3 3.4 4.5 5.6 6.7 7.8 8.9 9.1 : 986898.1800000002
0 0 0 0 0 0 0 0 0 0 : 9
1 1 1 1 1 1 1 1 1 1 : 0

A  => env/tests/sphere.txt +32 -0
@@ 1,32 @@
# Test data for Sphere function, with offset = (1,1,...,1)
0 : 1
0.5 : 0.25
1 : 0
-0.5 : 2.25
-5 : 36
5 : 16
0 0 : 2
-1 -1 : 8
-1 1 : 4
1 -1 : 4
1 1 : 0
-0.1 -0.2 : 2.6500000000000004
0.1 0.2 : 1.4500000000000002
-5 -5 : 72
-5 5 : 52
5 -5 : 52
5 5 : 32
0 0 0 : 3
1 1 1 : 0
-5 -5 -5 : 108
-5 -5 5 : 88
-5 5 -5 : 88
-5 5 5 : 68
5 -5 -5 : 88
5 -5 5 : 68
5 5 -5 : 68
5 5 5 : 48
-0.1 -1.2 -2.3 -3.4 -4.5 -5.6 -6.7 -7.8 -8.9 -9.1 : 446.85999999999996
0.1 1.2 2.3 3.4 4.5 5.6 6.7 7.8 8.9 9.1 : 248.45999999999998
0 0 0 0 0 0 0 0 0 0 : 10
1 1 1 1 1 1 1 1 1 1 : 0

A  => manifest.scm +8 -0
@@ 1,8 @@
(specifications->manifest
 (list
  "gdb"
  "gcc-toolchain"
  "julia"
  "rust"
  "rust-analyzer"
  "rust:cargo"))