finish random instruction for now
This commit is contained in:
parent
f68e9577d6
commit
e8f3910112
@ -29,7 +29,7 @@ pub fn make_random_plushy(
|
||||
}
|
||||
|
||||
/// A map of genes to their number of blocks they open.
|
||||
static OPEN_MAP: LazyLock<HashMap<Gene, u8>> = LazyLock::new(|| {
|
||||
pub static OPEN_MAP: LazyLock<HashMap<Gene, u8>> = LazyLock::new(|| {
|
||||
let mut temp_map = HashMap::default();
|
||||
temp_map.insert(StateFunc(exec_dup), 1u8);
|
||||
temp_map.insert(StateFunc(exec_dup_times), 1u8);
|
||||
|
@ -1,4 +1,5 @@
|
||||
use crate::gp::args::ClosingType;
|
||||
use crate::gp::genome::OPEN_MAP;
|
||||
use crate::push::state::Gene;
|
||||
use rand::Rng;
|
||||
use rand::seq::IndexedRandom;
|
||||
@ -12,9 +13,57 @@ pub fn random_instruction(
|
||||
match closing_type {
|
||||
ClosingType::Specified => return instructions.choose(rng).unwrap().clone(),
|
||||
ClosingType::Balanced => {
|
||||
let
|
||||
let source: Vec<Gene> = instructions
|
||||
.iter()
|
||||
.filter(|instr| !matches!(instr, Gene::Close))
|
||||
.cloned()
|
||||
.collect();
|
||||
let total_opens: usize = source
|
||||
.iter()
|
||||
.filter_map(|instr| {
|
||||
if let Gene::StateFunc(_) = instr {
|
||||
OPEN_MAP.get(instr).copied().map(|val| val as usize)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
.sum();
|
||||
let p = if source.is_empty() {
|
||||
0.0
|
||||
} else {
|
||||
total_opens as f64 / source.len() as f64
|
||||
};
|
||||
// Return Close or a random instruction based on probability
|
||||
if rng.random::<f64>() < p {
|
||||
Gene::Close
|
||||
} else {
|
||||
source.choose(rng).unwrap().clone()
|
||||
}
|
||||
}
|
||||
ClosingType::None => {
|
||||
// Find multi-block instructions (those with opens > 1)
|
||||
let multi_block_instructions: Vec<Gene> = instructions
|
||||
.iter()
|
||||
.filter(|instr| {
|
||||
if let Gene::StateFunc(_) = instr {
|
||||
OPEN_MAP.get(instr).map_or(false, |&opens| opens > 1)
|
||||
} else {
|
||||
false
|
||||
}
|
||||
})
|
||||
.cloned()
|
||||
.collect();
|
||||
|
||||
// Remove Close and multi-block instructions
|
||||
let source: Vec<Gene> = instructions
|
||||
.into_iter() // Take ownership of instructions
|
||||
.filter(|instr| {
|
||||
!matches!(instr, Gene::Close) && !multi_block_instructions.contains(instr)
|
||||
})
|
||||
.collect();
|
||||
|
||||
source.choose(rng).unwrap().clone()
|
||||
}
|
||||
_ => todo!(),
|
||||
}
|
||||
}
|
||||
|
||||
@ -33,3 +82,34 @@ pub fn gaussian_noise_factor(rng: &mut impl Rng) -> Decimal {
|
||||
|
||||
(dec!(-2.0) * u0.ln()).sqrt().unwrap() * (dec!(2.0) * rust_decimal::Decimal::PI * u1).cos()
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
use crate::instructions::code::*;
|
||||
use crate::instructions::common::boolean_rotate;
|
||||
use crate::instructions::vector::*;
|
||||
use crate::push::utils::most_genes;
|
||||
use rand::SeedableRng;
|
||||
use rand::rngs::StdRng;
|
||||
|
||||
#[test]
|
||||
fn random_instruction_test() {
|
||||
let mut rng = StdRng::seed_from_u64(42);
|
||||
let genes = most_genes();
|
||||
|
||||
let rand_instruction = random_instruction(genes.clone(), ClosingType::Specified, &mut rng);
|
||||
assert_eq!(
|
||||
Gene::StateFunc(vector_float_from_last_prim),
|
||||
rand_instruction
|
||||
);
|
||||
|
||||
let mut rng = StdRng::seed_from_u64(32038);
|
||||
let rand_instruction = random_instruction(genes.clone(), ClosingType::Balanced, &mut rng);
|
||||
assert_eq!(Gene::StateFunc(boolean_rotate), rand_instruction);
|
||||
|
||||
let mut rng = StdRng::seed_from_u64(3203890821);
|
||||
let rand_instruction = random_instruction(genes, ClosingType::None, &mut rng);
|
||||
assert_eq!(Gene::StateFunc(code_insert), rand_instruction);
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user