pub struct MeanSquaredError;
Expand description
Mean squared error loss function.
The MSE is calculated as the average of squared differences between predictions and targets: MSE = mean((predictions - targets)^2) It is commonly used for regression problems.
§Examples
use scirs2_neural::losses::MeanSquaredError;
use scirs2_neural::losses::Loss;
use scirs2_core::ndarray::{Array, arr1};
let mse = MeanSquaredError::new();
let predictions = arr1(&[1.0, 2.0, 3.0]).into_dyn();
let targets = arr1(&[1.5, 1.8, 2.5]).into_dyn();
// Forward pass to calculate loss
let loss = mse.forward(&predictions, &targets).unwrap();
// Backward pass to calculate gradients
let gradients = mse.backward(&predictions, &targets).unwrap();
Implementations§
Source§impl MeanSquaredError
impl MeanSquaredError
Sourcepub fn new() -> Self
pub fn new() -> Self
Create a new mean squared error loss function
Examples found in repository?
examples/improved_xor.rs (line 35)
28 fn train(
29 &mut self,
30 inputs: &Array<f32, IxDyn>,
31 targets: &Array<f32, IxDyn>,
32 learning_rate: f32,
33 epochs: usize,
34 ) -> Result<()> {
35 let loss_fn = MeanSquaredError::new();
36 println!("Training for {epochs} epochs");
37 for epoch in 0..epochs {
38 // Forward pass
39 let hidden_output = self.hidden_layer.forward(inputs)?;
40 let final_output = self.output_layer.forward(&hidden_output)?;
41 // Compute loss
42 let loss = loss_fn.forward(&final_output, targets)?;
43 if epoch % 500 == 0 || epoch == epochs - 1 {
44 println!("Epoch {}/{epochs}: loss = {loss:.6}", epoch + 1);
45 }
46 // Backward pass
47 let output_grad = loss_fn.backward(&final_output, targets)?;
48 let hidden_grad = self.output_layer.backward(&hidden_output, &output_grad)?;
49 let _input_grad = self.hidden_layer.backward(inputs, &hidden_grad)?;
50 // Custom update using direct access to the layers' fields
51 // Note: This is non-idiomatic as it breaks layer encapsulation
52 // but necessary due to implementation limitations
53 custom_update_layer(&mut self.hidden_layer, learning_rate)?;
54 custom_update_layer(&mut self.output_layer, learning_rate)?;
55 }
56 Ok(())
57 }
More examples
examples/manual_xor.rs (line 25)
9fn main() -> Result<()> {
10 println!("Manual XOR Neural Network Example");
11 // Create a simple dataset for XOR problem
12 let inputs = Array::from_shape_vec(
13 IxDyn(&[4, 2]),
14 vec![0.0f32, 0.0, 0.0, 1.0, 1.0, 0.0, 1.0, 1.0],
15 )?;
16 let targets = Array::from_shape_vec(IxDyn(&[4, 1]), vec![0.0f32, 1.0, 1.0, 0.0])?;
17 println!("XOR problem dataset:");
18 println!("Inputs:\n{inputs:?}");
19 println!("Targets:\n{targets:?}");
20 // Create neural network layers
21 let mut rng = SmallRng::from_seed([42; 32]);
22 let mut hidden_layer = Dense::new(2, 4, Some("relu"), &mut rng)?;
23 let mut output_layer = Dense::new(4, 1, None, &mut rng)?;
24 // Create loss function
25 let loss_fn = MeanSquaredError::new();
26 // Training parameters
27 let learning_rate = 0.5f32;
28 let num_epochs = 10000;
29 println!("\nTraining for {num_epochs} epochs");
30 for epoch in 0..num_epochs {
31 // Forward pass through the network
32 let hidden_output = hidden_layer.forward(&inputs)?;
33 let final_output = output_layer.forward(&hidden_output)?;
34 // Compute loss
35 let loss = loss_fn.forward(&final_output, &targets)?;
36 if epoch % 500 == 0 || epoch == num_epochs - 1 {
37 println!("Epoch {}/{num_epochs}: loss = {loss:.6}", epoch + 1);
38 }
39 // Backward pass
40 let output_grad = loss_fn.backward(&final_output, &targets)?;
41 let hidden_grad = output_layer.backward(&hidden_output, &output_grad)?;
42 let _input_grad = hidden_layer.backward(&inputs, &hidden_grad)?;
43 // Update parameters
44 hidden_layer.update(learning_rate)?;
45 output_layer.update(learning_rate)?;
46 }
47 // Evaluate the model
48 println!("\nEvaluation:");
49 let hidden_output = hidden_layer.forward(&inputs)?;
50 let final_output = output_layer.forward(&hidden_output)?;
51 println!("Predictions:\n{final_output:.3?}");
52 // Test with individual inputs
53 println!("\nTesting with specific inputs:");
54 let test_cases = vec![
55 (0.0f32, 0.0f32),
56 (0.0f32, 1.0f32),
57 (1.0f32, 0.0f32),
58 (1.0f32, 1.0f32),
59 ];
60 for (x1, x2) in test_cases {
61 let test_input = Array::from_shape_vec(IxDyn(&[1, 2]), vec![x1, x2])?;
62 let hidden_output = hidden_layer.forward(&test_input)?;
63 let prediction = output_layer.forward(&hidden_output)?;
64 let expected = if (x1 == 1.0 && x2 == 0.0) || (x1 == 0.0 && x2 == 1.0) {
65 1.0
66 } else {
67 0.0
68 };
69 println!(
70 "Input: [{x1:.1}, {x2:.1}], Predicted: {:.3}, Expected: {expected:.1}",
71 prediction[[0, 0]]
72 );
73 }
74 Ok(())
75}
examples/loss_functions_example.rs (line 11)
7fn main() -> Result<(), Box<dyn std::error::Error>> {
8 println!("Loss functions example");
9 // Mean Squared Error example
10 println!("\n--- Mean Squared Error Example ---");
11 let mse = MeanSquaredError::new();
12 // Create sample data for regression
13 let predictions = Array::from_vec(vec![1.0, 2.0, 3.0]).into_dyn();
14 let targets = Array::from_vec(vec![1.5, 1.8, 2.5]).into_dyn();
15 // Calculate loss
16 let loss = mse.forward(&predictions, &targets)?;
17 println!("Predictions: {predictions:?}");
18 println!("Targets: {targets:?}");
19 println!("MSE Loss: {loss:.4}");
20 // Calculate gradients
21 let gradients = mse.backward(&predictions, &targets)?;
22 println!("MSE Gradients: {gradients:?}");
23 // Cross-Entropy Loss example
24 println!("\n--- Cross-Entropy Loss Example ---");
25 let ce = CrossEntropyLoss::new(1e-10);
26 // Create sample data for multi-class classification
27 let predictions = Array::from_shape_vec(IxDyn(&[2, 3]), vec![0.7, 0.2, 0.1, 0.3, 0.6, 0.1])?;
28 let targets = Array::from_shape_vec(IxDyn(&[2, 3]), vec![1.0, 0.0, 0.0, 0.0, 1.0, 0.0])?;
29 let loss = ce.forward(&predictions, &targets)?;
30 println!("Predictions (probabilities):");
31 println!("{predictions:?}");
32 println!("Targets (one-hot):");
33 println!("{targets:?}");
34 println!("Cross-Entropy Loss: {loss:.4}");
35 let gradients = ce.backward(&predictions, &targets)?;
36 println!("Cross-Entropy Gradients:");
37 println!("{gradients:?}");
38 // Focal Loss example
39 println!("\n--- Focal Loss Example ---");
40 let focal = FocalLoss::new(2.0, Some(0.25), 1e-10);
41 // Create sample data for imbalanced classification
42 let loss = focal.forward(&predictions, &targets)?;
43 println!("Focal Loss (gamma=2.0, alpha=0.25): {loss:.4}");
44 let _gradients = focal.backward(&predictions, &targets)?;
45 println!("Focal Loss Gradients:");
46 // Contrastive Loss example
47 println!("\n--- Contrastive Loss Example ---");
48 let contrastive = ContrastiveLoss::new(1.0);
49 // Create sample data for similarity learning
50 // Embedding pairs (batch_size x 2 x embedding_dim)
51 let embeddings = Array::from_shape_vec(
52 IxDyn(&[2, 2, 3]),
53 vec![
54 0.1, 0.2, 0.3, // First pair, first embedding
55 0.1, 0.3, 0.3, // First pair, second embedding (similar)
56 0.5, 0.5, 0.5, // Second pair, first embedding
57 0.9, 0.8, 0.7, // Second pair, second embedding (dissimilar)
58 ],
59 )?;
60 // Labels: 1 for similar pairs, 0 for dissimilar
61 let labels = Array::from_shape_vec(IxDyn(&[2, 1]), vec![1.0, 0.0])?;
62 let loss = contrastive.forward(&embeddings, &labels)?;
63 println!("Embeddings (batch_size x 2 x embedding_dim):");
64 println!("{embeddings:?}");
65 println!("Labels (1 for similar, 0 for dissimilar):");
66 println!("{labels:?}");
67 println!("Contrastive Loss (margin=1.0): {loss:.4}");
68 let gradients = contrastive.backward(&embeddings, &labels)?;
69 println!("Contrastive Loss Gradients (first few):");
70 let gradient_slice = gradients.slice(scirs2_core::ndarray::s![0, .., 0]);
71 println!("{gradient_slice:?}");
72 // Triplet Loss example
73 println!("\n--- Triplet Loss Example ---");
74 let triplet = TripletLoss::new(0.5);
75 // Create sample data for triplet learning
76 // Embedding triplets (batch_size x 3 x embedding_dim)
77 let triplet_embeddings = Array3::from_shape_vec(
78 (2, 3, 3),
79 vec![
80 0.1, 0.2, 0.3, // First triplet, anchor
81 0.1, 0.3, 0.3, // First triplet, positive
82 0.5, 0.5, 0.5, // First triplet, negative
83 0.6, 0.6, 0.6, // Second triplet, anchor
84 0.5, 0.6, 0.6, // Second triplet, positive
85 0.1, 0.1, 0.1, // Second triplet, negative
86 ],
87 )?
88 .into_dyn();
89 // Dummy labels (not used by triplet loss)
90 let dummy_labels = Array::zeros(IxDyn(&[2, 1]));
91 let loss = triplet.forward(&triplet_embeddings, &dummy_labels)?;
92 println!("Embeddings (batch_size x 3 x embedding_dim):");
93 println!(" - First dimension: batch size");
94 println!(" - Second dimension: [anchor, positive, negative]");
95 println!(" - Third dimension: embedding components");
96 println!("Triplet Loss (margin=0.5): {loss:.4}");
97 let _gradients = triplet.backward(&triplet_embeddings, &dummy_labels)?;
98 println!("Triplet Loss Gradients (first few):");
99 Ok(())
100}
Trait Implementations§
Source§impl Clone for MeanSquaredError
impl Clone for MeanSquaredError
Source§fn clone(&self) -> MeanSquaredError
fn clone(&self) -> MeanSquaredError
Returns a duplicate of the value. Read more
1.0.0 · Source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
Performs copy-assignment from
source
. Read moreSource§impl Debug for MeanSquaredError
impl Debug for MeanSquaredError
Source§impl Default for MeanSquaredError
impl Default for MeanSquaredError
Source§impl<F: Float + Debug> Loss<F> for MeanSquaredError
impl<F: Float + Debug> Loss<F> for MeanSquaredError
impl Copy for MeanSquaredError
Auto Trait Implementations§
impl Freeze for MeanSquaredError
impl RefUnwindSafe for MeanSquaredError
impl Send for MeanSquaredError
impl Sync for MeanSquaredError
impl Unpin for MeanSquaredError
impl UnwindSafe for MeanSquaredError
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Mutably borrows from an owned value. Read more
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
Converts
self
into a Left
variant of Either<Self, Self>
if into_left
is true
.
Converts self
into a Right
variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
Converts
self
into a Left
variant of Either<Self, Self>
if into_left(&self)
returns true
.
Converts self
into a Right
variant of Either<Self, Self>
otherwise. Read more