Skip to content

Commit

Permalink
Merge branch 'features/error' into dev
Browse files Browse the repository at this point in the history
  • Loading branch information
Axect committed Apr 11, 2024
2 parents c72645d + 5c0657b commit 1b8bfc6
Show file tree
Hide file tree
Showing 2 changed files with 12 additions and 21 deletions.
1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ lapack = { version = "0.19", optional = true }
serde = { version = "1.0", features = ["derive"], optional = true }
json = { version = "0.12", optional = true }
arrow2 = { version = "0.18", features = ["io_parquet", "io_parquet_compression"], optional = true }
anyhow = "1.0.82"

[package.metadata.docs.rs]
rustdoc-args = [ "--html-in-header", "katex-header.html", "--cfg", "docsrs"]
Expand Down
32 changes: 11 additions & 21 deletions src/numerical/root.rs
Original file line number Diff line number Diff line change
@@ -1,17 +1,7 @@
use thiserror::Error;

#[derive(Error, Debug, Clone)]
pub enum RootFindingError {
#[error("No available root")]
NoAvailableRoot,
#[error("Zero derivative at {0}")]
ZeroDerivative(f64),
#[error("Constrain violated at {0}")]
ConstraintViolation(f64),
}
use anyhow::{Result, bail};

pub trait RootFindingProblem<T> {
fn function(&self, x: f64) -> Result<f64, RootFindingError>;
fn function(&self, x: f64) -> Result<f64>;
fn initial_guess(&self) -> T;
fn derivative(&self, x: f64) -> f64 {
unimplemented!()
Expand All @@ -22,11 +12,11 @@ pub trait RootFindingProblem<T> {
}

pub trait RootFindingMethod<T> {
fn step<P: RootFindingProblem<T>>(&self, problem: &P, state: T) -> Result<T, RootFindingError>;
fn step<P: RootFindingProblem<T>>(&self, problem: &P, state: T) -> Result<T>;
}

pub trait RootSolver {
fn solve<P, F, T>(&self, problem: &P, finder: &F) -> Result<f64, RootFindingError>
fn solve<P, F, T>(&self, problem: &P, finder: &F) -> Result<f64>
where
P: RootFindingProblem<T>,
F: RootFindingMethod<T>;
Expand All @@ -45,7 +35,7 @@ impl RootFindingMethod<(f64, f64)> for BisectionMethod {
&self,
problem: &P,
state: (f64, f64),
) -> Result<(f64, f64), RootFindingError> {
) -> Result<(f64, f64)> {
let (a, b) = state;
let c = (a + b) / 2.0;

Expand All @@ -60,7 +50,7 @@ impl RootFindingMethod<(f64, f64)> for BisectionMethod {
} else if fc == 0.0 {
Ok((c, c))
} else {
Err(RootFindingError::NoAvailableRoot)
bail!("There is no root in the interval [{}, {}]", a, b);
}
}
}
Expand All @@ -78,12 +68,12 @@ impl RootFindingMethod<f64> for NewtonMethod {
&self,
problem: &P,
state: f64,
) -> Result<f64, RootFindingError> {
) -> Result<f64> {
let f = problem.function(state)?;
let df = problem.derivative(state);

if df == 0.0 {
return Err(RootFindingError::ZeroDerivative(state));
bail!("Zero derivative at x = {}", state);
}

Ok(state - f / df)
Expand All @@ -103,15 +93,15 @@ impl RootFindingMethod<(f64, f64)> for SecantMethod {
&self,
problem: &P,
state: (f64, f64),
) -> Result<(f64, f64), RootFindingError> {
) -> Result<(f64, f64)> {
let (x0, x1) = state;
let f0 = problem.function(x0)?;
let f1 = problem.function(x1)?;

if f0 == f1 {
return Err(RootFindingError::ZeroDerivative(x0));
bail!("Zero secant at ({}, {})", x0, x1);
}

unimplemented!()
Ok((x1, x1 - f1 * (x1 - x0) / (f1 - f0)))
}
}

0 comments on commit 1b8bfc6

Please sign in to comment.