oxineat_nn/
lib.rs

1//! # OxiNEAT-NN
2//! An neural network-based implementation of the [`OxiNEAT` crate](https://crates.io/crates/oxineat)'s `Genome` trait.
3//! 
4//! Provides a [`NNGenome`] type usable in `OxiNEAT` `Population`s, as well as two neural network implementations which can be generated from an [`NNGenome`]:
5//! - [`RealTimeNetwork`]: best suited for real-time control tasks, with new inputs set for each activation, and multiple time-steps involved.
6//! - [`FunctionApproximatorNetwork`]: best suited for more instantaneous single-output-per-input function approximation tasks.
7//! 
8//! [`NNGenome`]: crate::genomics::NNGenome
9//! [`RealTimeNetwork`]: crate::networks::RealTimeNetwork
10//! [`FunctionApproximatorNetwork`]: crate::networks::FunctionApproximatorNetwork
11//! 
12//! # Example usage: Evolution of XOR function approximator
13//! ```
14//! use oxineat::{Population, PopulationConfig};
15//! use oxineat_nn::{
16//!     genomics::{ActivationType, GeneticConfig, NNGenome},
17//!     networks::FunctionApproximatorNetwork,
18//! };
19//! use serde_json;
20//! use std::num::NonZeroUsize;
21//! 
22//! // Allowed error margin for neural net answers.
23//! const ERROR_MARGIN: f32 = 0.3;
24//! 
25//! fn evaluate_xor(genome: &NNGenome) -> f32 {
26//!     let mut network = FunctionApproximatorNetwork::from::<1>(genome);
27//!
28//!     let values = [
29//!         ([1.0, 0.0, 0.0], 0.0),
30//!         ([1.0, 0.0, 1.0], 1.0),
31//!         ([1.0, 1.0, 0.0], 1.0),
32//!         ([1.0, 1.0, 1.0], 0.0),
33//!     ];
34//!
35//!     let mut errors = [0.0, 0.0, 0.0, 0.0];
36//!     for (i, (input, output)) in values.iter().enumerate() {
37//!         errors[i] = (network.evaluate_at(input)[0] - output).abs();
38//!         if errors[i] < ERROR_MARGIN {
39//!             errors[i] = 0.0;
40//!         }
41//!     }
42//!
43//!     (4.0 - errors.iter().copied().sum::<f32>()).powf(2.0)
44//! }
45//!
46//! fn main() {
47//!     let genetic_config = GeneticConfig {
48//!         input_count: NonZeroUsize::new(3).unwrap(),
49//!         output_count: NonZeroUsize::new(1).unwrap(),
50//!         activation_types: vec![ActivationType::Sigmoid],
51//!         output_activation_types: vec![ActivationType::Sigmoid],
52//!         child_mutation_chance: 0.65,
53//!         mate_by_averaging_chance: 0.4,
54//!         suppression_reset_chance: 1.0,
55//!         initial_expression_chance: 1.0,
56//!         weight_bound: 5.0,
57//!         weight_reset_chance: 0.2,
58//!         weight_nudge_chance: 0.9,
59//!         weight_mutation_power: 2.5,
60//!         node_addition_mutation_chance: 0.03,
61//!         gene_addition_mutation_chance: 0.05,
62//!         max_gene_addition_mutation_attempts: 20,
63//!         recursion_chance: 0.0,
64//!         excess_gene_factor: 1.0,
65//!         disjoint_gene_factor: 1.0,
66//!         common_weight_factor: 0.4,
67//!         ..GeneticConfig::zero()
68//!     };
69//!
70//!     let population_config = PopulationConfig {
71//!         size: NonZeroUsize::new(150).unwrap(),
72//!         distance_threshold: 3.0,
73//!         elitism: 1,
74//!         survival_threshold: 0.2,
75//!         sexual_reproduction_chance: 0.6,
76//!         adoption_rate: 1.0,
77//!         interspecies_mating_chance: 0.001,
78//!         stagnation_threshold: NonZeroUsize::new(15).unwrap(),
79//!         stagnation_penalty: 1.0,
80//!     };
81//! 
82//!     let mut population = Population::new(population_config, genetic_config);
83//!     for _ in 0..100 {
84//!         population.evaluate_fitness(evaluate_xor);
85//!         if (population.champion().fitness() - 16.0).abs() < f32::EPSILON {
86//!             println!("Solution found!: {}", serde_json::to_string(&population.champion()).unwrap());
87//!             break;
88//!         }
89//!         if let Err(e) = population.evolve() {
90//!             eprintln!("{}", e);
91//!             break;
92//!         }
93//!     }
94//! }
95//! ```
96
97pub mod genomics;
98pub mod networks;
99
100/// Identifier type used to designate historically
101/// identical mutations for the purposes of
102/// genome comparison and genetic tracking.
103pub type Innovation = usize;