fix: update kernel common
This commit is contained in:
@@ -1,6 +1,41 @@
|
|||||||
use strum_macros::EnumIter;
|
use strum_macros::EnumIter;
|
||||||
use thiserror::Error as TeError;
|
use thiserror::Error as TeError;
|
||||||
|
|
||||||
|
// region: Sanitizer
|
||||||
|
|
||||||
|
#[derive(Debug, TeError)]
|
||||||
|
#[error("given floating value {0} is invalid")]
|
||||||
|
pub struct FloatingPointError(f64);
|
||||||
|
|
||||||
|
pub fn sanitize_floating_point(f: f64) -> Result<f64, FloatingPointError> {
|
||||||
|
if f.is_finite() {
|
||||||
|
Ok(f)
|
||||||
|
} else {
|
||||||
|
Err(FloatingPointError(f))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, TeError)]
|
||||||
|
pub enum DeviceValueError {
|
||||||
|
#[error("{0}")]
|
||||||
|
BadFloatingPoint(#[from] FloatingPointError),
|
||||||
|
#[error("given device value {0} is out of range")]
|
||||||
|
OutOfRange(f64),
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn sanitize_device_value(f: f64) -> Result<f64, DeviceValueError> {
|
||||||
|
let f = sanitize_floating_point(f)?;
|
||||||
|
if f > 0f64 {
|
||||||
|
Ok(f)
|
||||||
|
} else {
|
||||||
|
Err(DeviceValueError::OutOfRange(f))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|
||||||
|
// region: Circuit Utilities
|
||||||
|
|
||||||
/// The kind of device.
|
/// The kind of device.
|
||||||
#[derive(Debug, Clone, Copy)]
|
#[derive(Debug, Clone, Copy)]
|
||||||
pub enum DeviceKind {
|
pub enum DeviceKind {
|
||||||
@@ -35,82 +70,6 @@ impl JointKind {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Error occurs when manipulating [SubCircuit].
|
|
||||||
#[derive(Debug, TeError)]
|
|
||||||
pub enum SubCircuitError {
|
|
||||||
#[error("given circuit device value {0} should greater than zero")]
|
|
||||||
BadDeviceValue(f64),
|
|
||||||
#[error("the previous computed circuit value {0} should greater than zero")]
|
|
||||||
BadPreviousValue(f64),
|
|
||||||
#[error("bad float point arithmetic")]
|
|
||||||
BadArithmetic,
|
|
||||||
}
|
|
||||||
|
|
||||||
/// The part of circuit composed of two devices and the joint kind.
|
|
||||||
#[derive(Debug, Clone)]
|
|
||||||
pub struct SubCircuit {
|
|
||||||
/// The value of the device.
|
|
||||||
device_value: f64,
|
|
||||||
/// The joint kind between this device and the next device.
|
|
||||||
joint_kind: JointKind,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl SubCircuit {
|
|
||||||
/// Initialize subcircuit with given device value and joint kind.
|
|
||||||
///
|
|
||||||
/// The input device value should greater than zero,
|
|
||||||
/// otherwise an error will return.
|
|
||||||
pub fn new(device_value: f64, joint_kind: JointKind) -> Result<Self, SubCircuitError> {
|
|
||||||
if device_value > 0f64 {
|
|
||||||
Ok(Self {
|
|
||||||
device_value,
|
|
||||||
joint_kind,
|
|
||||||
})
|
|
||||||
} else {
|
|
||||||
Err(SubCircuitError::BadDeviceValue(device_value))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Compute the joint value with given previous computed value and device kind.
|
|
||||||
///
|
|
||||||
/// Parameter `value` should be the value computed from previous devices.
|
|
||||||
/// And it should greater than zero.
|
|
||||||
/// `device_kind` is the kind of the device.
|
|
||||||
pub fn compute(&self, value: f64, device_kind: DeviceKind) -> Result<f64, SubCircuitError> {
|
|
||||||
// Check the range of provided value for computing
|
|
||||||
if !(value > 0f64) {
|
|
||||||
return Err(SubCircuitError::BadPreviousValue(value));
|
|
||||||
}
|
|
||||||
|
|
||||||
// We perform series connect for: series resistor, series inductor and parallel capacitor.
|
|
||||||
// We perform parallel connect for: parallel resistor, parallel inductor and series capacitor.
|
|
||||||
let joint_kind = match device_kind {
|
|
||||||
DeviceKind::Capacitor => self.joint_kind.flip(),
|
|
||||||
_ => self.joint_kind,
|
|
||||||
};
|
|
||||||
|
|
||||||
let rv = match joint_kind {
|
|
||||||
JointKind::Series => self.device_value + value,
|
|
||||||
JointKind::Parallel => (self.device_value * value) / (self.device_value + value),
|
|
||||||
};
|
|
||||||
if rv.is_finite() {
|
|
||||||
Ok(rv)
|
|
||||||
} else {
|
|
||||||
Err(SubCircuitError::BadArithmetic)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Get the device value.
|
|
||||||
pub fn device_value(&self) -> f64 {
|
|
||||||
self.device_value
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Get the joint kind.
|
|
||||||
pub fn joint_kind(&self) -> JointKind {
|
|
||||||
self.joint_kind
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// The scale of devices in the circuit.
|
/// The scale of devices in the circuit.
|
||||||
#[derive(Debug, Clone, Copy)]
|
#[derive(Debug, Clone, Copy)]
|
||||||
pub enum CircuitDeviceScale {
|
pub enum CircuitDeviceScale {
|
||||||
@@ -134,11 +93,84 @@ impl CircuitDeviceScale {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|
||||||
|
// region: Circuit Stuff
|
||||||
|
|
||||||
|
/// Error occurs when manipulating [SubCircuit].
|
||||||
|
#[derive(Debug, TeError)]
|
||||||
|
pub enum SubCircuitError {
|
||||||
|
#[error("invalid device value in circuit: {0}")]
|
||||||
|
BadDeviceValue(DeviceValueError),
|
||||||
|
#[error("bad previous computed circuit value: {0}")]
|
||||||
|
BadPreviousValue(DeviceValueError),
|
||||||
|
#[error("arithmetic error: {0}")]
|
||||||
|
BadArithmetic(FloatingPointError),
|
||||||
|
}
|
||||||
|
|
||||||
|
/// The part of circuit composed of two devices and the joint kind.
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct SubCircuit {
|
||||||
|
/// The value of the device.
|
||||||
|
device_value: f64,
|
||||||
|
/// The joint kind between this device and the next device.
|
||||||
|
joint_kind: JointKind,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl SubCircuit {
|
||||||
|
/// Initialize subcircuit with given device value and joint kind.
|
||||||
|
///
|
||||||
|
/// The input device value should greater than zero,
|
||||||
|
/// otherwise an error will return.
|
||||||
|
pub fn new(device_value: f64, joint_kind: JointKind) -> Result<Self, SubCircuitError> {
|
||||||
|
let device_value = sanitize_device_value(device_value)
|
||||||
|
.map_err(|err| SubCircuitError::BadDeviceValue(err))?;
|
||||||
|
Ok(Self {
|
||||||
|
device_value,
|
||||||
|
joint_kind,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Compute the joint value with given previous computed value and device kind.
|
||||||
|
///
|
||||||
|
/// Parameter `value` should be the value computed from previous devices.
|
||||||
|
/// And it should greater than zero.
|
||||||
|
/// `device_kind` is the kind of the device.
|
||||||
|
pub fn compute(&self, value: f64, device_kind: DeviceKind) -> Result<f64, SubCircuitError> {
|
||||||
|
// Check the range of provided value for computing
|
||||||
|
let value =
|
||||||
|
sanitize_device_value(value).map_err(|err| SubCircuitError::BadPreviousValue(err))?;
|
||||||
|
|
||||||
|
// We perform series connect for: series resistor, series inductor and parallel capacitor.
|
||||||
|
// We perform parallel connect for: parallel resistor, parallel inductor and series capacitor.
|
||||||
|
let joint_kind = match device_kind {
|
||||||
|
DeviceKind::Capacitor => self.joint_kind.flip(),
|
||||||
|
_ => self.joint_kind,
|
||||||
|
};
|
||||||
|
|
||||||
|
sanitize_floating_point(match joint_kind {
|
||||||
|
JointKind::Series => self.device_value + value,
|
||||||
|
JointKind::Parallel => (self.device_value * value) / (self.device_value + value),
|
||||||
|
})
|
||||||
|
.map_err(|err| SubCircuitError::BadArithmetic(err))
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Get the device value.
|
||||||
|
pub fn device_value(&self) -> f64 {
|
||||||
|
self.device_value
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Get the joint kind.
|
||||||
|
pub fn joint_kind(&self) -> JointKind {
|
||||||
|
self.joint_kind
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// Error occurs when manipulating [Circuit].
|
/// Error occurs when manipulating [Circuit].
|
||||||
#[derive(Debug, TeError)]
|
#[derive(Debug, TeError)]
|
||||||
pub enum CircuitError {
|
pub enum CircuitError {
|
||||||
#[error("given circuit device value {0} should greater than zero")]
|
#[error("invalid device value in circuit: {0}")]
|
||||||
BadDeviceValue(f64),
|
BadDeviceValue(DeviceValueError),
|
||||||
#[error("third device cannot exist without second device when building circuit")]
|
#[error("third device cannot exist without second device when building circuit")]
|
||||||
BlankSecondSubCircuit,
|
BlankSecondSubCircuit,
|
||||||
#[error("{0}")]
|
#[error("{0}")]
|
||||||
@@ -170,9 +202,8 @@ impl Circuit {
|
|||||||
third_device_subckt: Option<SubCircuit>,
|
third_device_subckt: Option<SubCircuit>,
|
||||||
) -> Result<Self, CircuitError> {
|
) -> Result<Self, CircuitError> {
|
||||||
// Check the value of first device
|
// Check the value of first device
|
||||||
if !(first_device_value > 0f64) {
|
let first_device_value = sanitize_device_value(first_device_value)
|
||||||
return Err(CircuitError::BadDeviceValue(first_device_value));
|
.map_err(|err| CircuitError::BadDeviceValue(err))?;
|
||||||
}
|
|
||||||
// Check impossible form
|
// Check impossible form
|
||||||
if second_device_subckt.is_none() && third_device_subckt.is_some() {
|
if second_device_subckt.is_none() && third_device_subckt.is_some() {
|
||||||
return Err(CircuitError::BlankSecondSubCircuit);
|
return Err(CircuitError::BlankSecondSubCircuit);
|
||||||
@@ -292,14 +323,14 @@ impl Circuit {
|
|||||||
/// Error occurs when manipulating [CircuitCalculator].
|
/// Error occurs when manipulating [CircuitCalculator].
|
||||||
#[derive(Debug, TeError)]
|
#[derive(Debug, TeError)]
|
||||||
pub enum CircuitCalculatorError {
|
pub enum CircuitCalculatorError {
|
||||||
#[error("given target value {0} should be greater than zero")]
|
#[error("invalid target value: {0}")]
|
||||||
BadTargetValue(f64),
|
BadTargetValue(DeviceValueError),
|
||||||
#[error("{0}")]
|
#[error("{0}")]
|
||||||
Circuit(#[from] CircuitError),
|
Circuit(#[from] CircuitError),
|
||||||
#[error("bad float point arithmetic")]
|
#[error("arithmetic error: {0}")]
|
||||||
BadArithmetic,
|
BadArithmetic(FloatingPointError),
|
||||||
#[error("provided value {0} reducing computation steps is invalid")]
|
#[error("bad provided value reducing computation steps: {0}")]
|
||||||
BadReuseValue(f64),
|
BadReuseValue(FloatingPointError),
|
||||||
}
|
}
|
||||||
|
|
||||||
/// The helper for circuit value computation.
|
/// The helper for circuit value computation.
|
||||||
@@ -314,14 +345,12 @@ pub struct CircuitCalculator {
|
|||||||
impl CircuitCalculator {
|
impl CircuitCalculator {
|
||||||
/// Initialize this calculator with given device kind and target value.
|
/// Initialize this calculator with given device kind and target value.
|
||||||
pub fn new(device_kind: DeviceKind, target_value: f64) -> Result<Self, CircuitCalculatorError> {
|
pub fn new(device_kind: DeviceKind, target_value: f64) -> Result<Self, CircuitCalculatorError> {
|
||||||
if target_value > 0f64 {
|
let target_value = sanitize_device_value(target_value)
|
||||||
|
.map_err(|err| CircuitCalculatorError::BadTargetValue(err))?;
|
||||||
Ok(Self {
|
Ok(Self {
|
||||||
device_kind,
|
device_kind,
|
||||||
target_value,
|
target_value,
|
||||||
})
|
})
|
||||||
} else {
|
|
||||||
Err(CircuitCalculatorError::BadTargetValue(target_value))
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// The value of this circuit.
|
/// The value of this circuit.
|
||||||
@@ -343,22 +372,13 @@ impl CircuitCalculator {
|
|||||||
value: Option<f64>,
|
value: Option<f64>,
|
||||||
) -> Result<f64, CircuitCalculatorError> {
|
) -> Result<f64, CircuitCalculatorError> {
|
||||||
let value = match value {
|
let value = match value {
|
||||||
Some(v) => {
|
Some(v) => sanitize_floating_point(v)
|
||||||
if v.is_finite() {
|
.map_err(|err| CircuitCalculatorError::BadReuseValue(err))?,
|
||||||
v
|
|
||||||
} else {
|
|
||||||
return Err(CircuitCalculatorError::BadReuseValue(v));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
None => self.value(circuit)?,
|
None => self.value(circuit)?,
|
||||||
};
|
};
|
||||||
|
|
||||||
let rv = value - self.target_value;
|
sanitize_floating_point(value - self.target_value)
|
||||||
if rv.is_finite() {
|
.map_err(|err| CircuitCalculatorError::BadArithmetic(err))
|
||||||
Ok(rv)
|
|
||||||
} else {
|
|
||||||
Err(CircuitCalculatorError::BadArithmetic)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// The unsigned difference between the target value and the value of this circuit.
|
/// The unsigned difference between the target value and the value of this circuit.
|
||||||
@@ -376,22 +396,13 @@ impl CircuitCalculator {
|
|||||||
difference: Option<f64>,
|
difference: Option<f64>,
|
||||||
) -> Result<f64, CircuitCalculatorError> {
|
) -> Result<f64, CircuitCalculatorError> {
|
||||||
let diff = match difference {
|
let diff = match difference {
|
||||||
Some(d) => {
|
Some(d) => sanitize_floating_point(d)
|
||||||
if d.is_finite() {
|
.map_err(|err| CircuitCalculatorError::BadReuseValue(err))?,
|
||||||
d
|
|
||||||
} else {
|
|
||||||
return Err(CircuitCalculatorError::BadReuseValue(d));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
None => self.difference(circuit, value)?,
|
None => self.difference(circuit, value)?,
|
||||||
};
|
};
|
||||||
|
|
||||||
let rv = diff.abs();
|
sanitize_floating_point(diff.abs())
|
||||||
if rv.is_finite() {
|
.map_err(|err| CircuitCalculatorError::BadArithmetic(err))
|
||||||
Ok(rv)
|
|
||||||
} else {
|
|
||||||
Err(CircuitCalculatorError::BadArithmetic)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// The signed relative difference between the target value and the value of this circuit.
|
/// The signed relative difference between the target value and the value of this circuit.
|
||||||
@@ -412,22 +423,13 @@ impl CircuitCalculator {
|
|||||||
difference: Option<f64>,
|
difference: Option<f64>,
|
||||||
) -> Result<f64, CircuitCalculatorError> {
|
) -> Result<f64, CircuitCalculatorError> {
|
||||||
let diff = match difference {
|
let diff = match difference {
|
||||||
Some(d) => {
|
Some(d) => sanitize_floating_point(d)
|
||||||
if d.is_finite() {
|
.map_err(|err| CircuitCalculatorError::BadReuseValue(err))?,
|
||||||
d
|
|
||||||
} else {
|
|
||||||
return Err(CircuitCalculatorError::BadReuseValue(d));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
None => self.difference(circuit, value)?,
|
None => self.difference(circuit, value)?,
|
||||||
};
|
};
|
||||||
|
|
||||||
let rv = diff / self.target_value;
|
sanitize_floating_point(diff / self.target_value)
|
||||||
if rv.is_finite() {
|
.map_err(|err| CircuitCalculatorError::BadArithmetic(err))
|
||||||
Ok(rv)
|
|
||||||
} else {
|
|
||||||
Err(CircuitCalculatorError::BadArithmetic)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// The unsigned relative difference between the target value and the value of this circuit.
|
/// The unsigned relative difference between the target value and the value of this circuit.
|
||||||
@@ -450,21 +452,14 @@ impl CircuitCalculator {
|
|||||||
relative_difference: Option<f64>,
|
relative_difference: Option<f64>,
|
||||||
) -> Result<f64, CircuitCalculatorError> {
|
) -> Result<f64, CircuitCalculatorError> {
|
||||||
let rel_diff = match relative_difference {
|
let rel_diff = match relative_difference {
|
||||||
Some(rd) => {
|
Some(rd) => sanitize_floating_point(rd)
|
||||||
if rd.is_finite() {
|
.map_err(|err| CircuitCalculatorError::BadReuseValue(err))?,
|
||||||
rd
|
|
||||||
} else {
|
|
||||||
return Err(CircuitCalculatorError::BadReuseValue(rd));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
None => self.relative_difference(circuit, value, difference)?,
|
None => self.relative_difference(circuit, value, difference)?,
|
||||||
};
|
};
|
||||||
|
|
||||||
let rv = rel_diff.abs();
|
sanitize_floating_point(rel_diff.abs())
|
||||||
if rv.is_finite() {
|
.map_err(|err| CircuitCalculatorError::BadArithmetic(err))
|
||||||
Ok(rv)
|
|
||||||
} else {
|
|
||||||
Err(CircuitCalculatorError::BadArithmetic)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|||||||
@@ -1,7 +1,12 @@
|
|||||||
|
use thiserror::Error as TeError;
|
||||||
use std::collections::HashSet;
|
use std::collections::HashSet;
|
||||||
use std::path::Path;
|
use std::path::Path;
|
||||||
|
|
||||||
use crate::common::LcrConnError;
|
/// Error occurs when building dataset.
|
||||||
|
#[derive(Debug, TeError)]
|
||||||
|
pub enum DatasetError {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
/// An item in the dataset.
|
/// An item in the dataset.
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
@@ -17,14 +22,14 @@ impl DatasetItem {
|
|||||||
///
|
///
|
||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// Returns [`LcrConnError::InvalidDatasetValue`] if the value is not greater than 0.
|
/// Returns [`DatasetError::InvalidDatasetValue`] if the value is not greater than 0.
|
||||||
/// Returns [`LcrConnError::EmptyDatasetItem`] if the string value is empty.
|
/// Returns [`DatasetError::EmptyDatasetItem`] if the string value is empty.
|
||||||
pub fn new(value: f64, str_value: String) -> Result<Self, LcrConnError> {
|
pub fn new(value: f64, str_value: String) -> Result<Self, DatasetError> {
|
||||||
if value <= 0.0 {
|
if value <= 0.0 {
|
||||||
return Err(LcrConnError::InvalidDatasetValue(value));
|
return Err(DatasetError::InvalidDatasetValue(value));
|
||||||
}
|
}
|
||||||
if str_value.is_empty() {
|
if str_value.is_empty() {
|
||||||
return Err(LcrConnError::EmptyDatasetItem);
|
return Err(DatasetError::EmptyDatasetItem);
|
||||||
}
|
}
|
||||||
Ok(Self { value, str_value })
|
Ok(Self { value, str_value })
|
||||||
}
|
}
|
||||||
@@ -46,10 +51,10 @@ impl Dataset {
|
|||||||
///
|
///
|
||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// Returns [`LcrConnError::DuplicateDatasetItem`] if duplicate values are found.
|
/// Returns [`DatasetError::DuplicateDatasetItem`] if duplicate values are found.
|
||||||
/// Returns [`LcrConnError::EmptyDataset`] if the iterable produces no items.
|
/// Returns [`DatasetError::EmptyDataset`] if the iterable produces no items.
|
||||||
/// Returns [`LcrConnError::InvalidHumanReadableValue`] if a value cannot be parsed.
|
/// Returns [`DatasetError::InvalidHumanReadableValue`] if a value cannot be parsed.
|
||||||
pub fn from_iterable<I, S>(str_values: I) -> Result<Self, LcrConnError>
|
pub fn from_iterable<I, S>(str_values: I) -> Result<Self, DatasetError>
|
||||||
where
|
where
|
||||||
I: IntoIterator<Item = S>,
|
I: IntoIterator<Item = S>,
|
||||||
S: Into<String>,
|
S: Into<String>,
|
||||||
@@ -64,7 +69,7 @@ impl Dataset {
|
|||||||
let value = from_human_readable_value(&str_value)?;
|
let value = from_human_readable_value(&str_value)?;
|
||||||
// Check and update set
|
// Check and update set
|
||||||
if !seen.insert(value) {
|
if !seen.insert(value) {
|
||||||
return Err(LcrConnError::DuplicateDatasetItem(str_value));
|
return Err(DatasetError::DuplicateDatasetItem(str_value));
|
||||||
}
|
}
|
||||||
// Add into result
|
// Add into result
|
||||||
items.push(DatasetItem::new(value, str_value)?);
|
items.push(DatasetItem::new(value, str_value)?);
|
||||||
@@ -72,7 +77,7 @@ impl Dataset {
|
|||||||
|
|
||||||
// Check empty case
|
// Check empty case
|
||||||
if items.is_empty() {
|
if items.is_empty() {
|
||||||
return Err(LcrConnError::EmptyDataset);
|
return Err(DatasetError::EmptyDataset);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Ok, assign it
|
// Ok, assign it
|
||||||
@@ -86,7 +91,7 @@ impl Dataset {
|
|||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// See [`Dataset::from_iterable`].
|
/// See [`Dataset::from_iterable`].
|
||||||
pub fn from_text(text: &str) -> Result<Self, LcrConnError> {
|
pub fn from_text(text: &str) -> Result<Self, DatasetError> {
|
||||||
let lines: Vec<String> = text
|
let lines: Vec<String> = text
|
||||||
.lines()
|
.lines()
|
||||||
.map(|line| line.trim().to_string())
|
.map(|line| line.trim().to_string())
|
||||||
@@ -99,9 +104,9 @@ impl Dataset {
|
|||||||
///
|
///
|
||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// Returns [`LcrConnError::Io`] if the file cannot be read.
|
/// Returns [`DatasetError::Io`] if the file cannot be read.
|
||||||
/// See [`Dataset::from_iterable`] for other errors.
|
/// See [`Dataset::from_iterable`] for other errors.
|
||||||
pub fn from_file(path: impl AsRef<Path>) -> Result<Self, LcrConnError> {
|
pub fn from_file(path: impl AsRef<Path>) -> Result<Self, DatasetError> {
|
||||||
let text = std::fs::read_to_string(path)?;
|
let text = std::fs::read_to_string(path)?;
|
||||||
Self::from_text(&text)
|
Self::from_text(&text)
|
||||||
}
|
}
|
||||||
@@ -111,7 +116,7 @@ impl Dataset {
|
|||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// See [`Dataset::from_iterable`].
|
/// See [`Dataset::from_iterable`].
|
||||||
pub fn resistor_preset() -> Result<Self, LcrConnError> {
|
pub fn resistor_preset() -> Result<Self, DatasetError> {
|
||||||
Self::from_iterable([
|
Self::from_iterable([
|
||||||
"100", "220", "270", "390", "470", "680", "1k", "1.2k", "1.5k", "2.2k", "3.3k",
|
"100", "220", "270", "390", "470", "680", "1k", "1.2k", "1.5k", "2.2k", "3.3k",
|
||||||
"4.7k", "6.8k", "10k", "47k", "100k", "1M",
|
"4.7k", "6.8k", "10k", "47k", "100k", "1M",
|
||||||
@@ -123,7 +128,7 @@ impl Dataset {
|
|||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// See [`Dataset::from_iterable`].
|
/// See [`Dataset::from_iterable`].
|
||||||
pub fn capacitor_preset() -> Result<Self, LcrConnError> {
|
pub fn capacitor_preset() -> Result<Self, DatasetError> {
|
||||||
Self::from_iterable([
|
Self::from_iterable([
|
||||||
"10p", "22p", "33p", "47p", "68p", "100p", "150p", "220p", "330p", "470p", "560p",
|
"10p", "22p", "33p", "47p", "68p", "100p", "150p", "220p", "330p", "470p", "560p",
|
||||||
"1u", "2.2u", "3.3u", "4.7u", "10u", "22u", "47u", "100u", "220u", "470u",
|
"1u", "2.2u", "3.3u", "4.7u", "10u", "22u", "47u", "100u", "220u", "470u",
|
||||||
@@ -135,7 +140,7 @@ impl Dataset {
|
|||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// See [`Dataset::from_iterable`].
|
/// See [`Dataset::from_iterable`].
|
||||||
pub fn inductor_preset() -> Result<Self, LcrConnError> {
|
pub fn inductor_preset() -> Result<Self, DatasetError> {
|
||||||
Self::from_iterable([
|
Self::from_iterable([
|
||||||
"0.1u", "0.15u", "0.47u", "0.68u", "1u", "1.5u", "2.2u", "3.3u", "4.7u", "6.8u",
|
"0.1u", "0.15u", "0.47u", "0.68u", "1u", "1.5u", "2.2u", "3.3u", "4.7u", "6.8u",
|
||||||
"8.2u", "10u", "15u", "22u", "33u", "47u", "68u", "100u",
|
"8.2u", "10u", "15u", "22u", "33u", "47u", "68u", "100u",
|
||||||
@@ -155,8 +160,8 @@ impl Dataset {
|
|||||||
///
|
///
|
||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// Returns [`LcrConnError::Io`] if the file cannot be written.
|
/// Returns [`DatasetError::Io`] if the file cannot be written.
|
||||||
pub fn save_file(&self, path: impl AsRef<Path>) -> Result<(), LcrConnError> {
|
pub fn save_file(&self, path: impl AsRef<Path>) -> Result<(), DatasetError> {
|
||||||
std::fs::write(path, self.save_text())?;
|
std::fs::write(path, self.save_text())?;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
@@ -206,7 +211,7 @@ impl DatasetCollection {
|
|||||||
resistor: I1,
|
resistor: I1,
|
||||||
capacitor: I2,
|
capacitor: I2,
|
||||||
inductor: I3,
|
inductor: I3,
|
||||||
) -> Result<Self, LcrConnError>
|
) -> Result<Self, DatasetError>
|
||||||
where
|
where
|
||||||
I1: IntoIterator<Item = S1>,
|
I1: IntoIterator<Item = S1>,
|
||||||
S1: Into<String>,
|
S1: Into<String>,
|
||||||
@@ -233,7 +238,7 @@ impl DatasetCollection {
|
|||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// See [`Dataset::from_text`].
|
/// See [`Dataset::from_text`].
|
||||||
pub fn from_text(resistor: &str, capacitor: &str, inductor: &str) -> Result<Self, LcrConnError> {
|
pub fn from_text(resistor: &str, capacitor: &str, inductor: &str) -> Result<Self, DatasetError> {
|
||||||
Ok(Self {
|
Ok(Self {
|
||||||
resistor: Dataset::from_text(resistor)?,
|
resistor: Dataset::from_text(resistor)?,
|
||||||
capacitor: Dataset::from_text(capacitor)?,
|
capacitor: Dataset::from_text(capacitor)?,
|
||||||
@@ -256,7 +261,7 @@ impl DatasetCollection {
|
|||||||
resistor: impl AsRef<Path>,
|
resistor: impl AsRef<Path>,
|
||||||
capacitor: impl AsRef<Path>,
|
capacitor: impl AsRef<Path>,
|
||||||
inductor: impl AsRef<Path>,
|
inductor: impl AsRef<Path>,
|
||||||
) -> Result<Self, LcrConnError> {
|
) -> Result<Self, DatasetError> {
|
||||||
Ok(Self {
|
Ok(Self {
|
||||||
resistor: Dataset::from_file(resistor)?,
|
resistor: Dataset::from_file(resistor)?,
|
||||||
capacitor: Dataset::from_file(capacitor)?,
|
capacitor: Dataset::from_file(capacitor)?,
|
||||||
@@ -269,7 +274,7 @@ impl DatasetCollection {
|
|||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// See [`Dataset::from_iterable`].
|
/// See [`Dataset::from_iterable`].
|
||||||
pub fn devices_preset() -> Result<Self, LcrConnError> {
|
pub fn devices_preset() -> Result<Self, DatasetError> {
|
||||||
Ok(Self {
|
Ok(Self {
|
||||||
resistor: Dataset::resistor_preset()?,
|
resistor: Dataset::resistor_preset()?,
|
||||||
capacitor: Dataset::capacitor_preset()?,
|
capacitor: Dataset::capacitor_preset()?,
|
||||||
@@ -300,13 +305,13 @@ impl DatasetCollection {
|
|||||||
///
|
///
|
||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// Returns [`LcrConnError::Io`] if any file cannot be written.
|
/// Returns [`DatasetError::Io`] if any file cannot be written.
|
||||||
pub fn save_file(
|
pub fn save_file(
|
||||||
&self,
|
&self,
|
||||||
resistor: impl AsRef<Path>,
|
resistor: impl AsRef<Path>,
|
||||||
capacitor: impl AsRef<Path>,
|
capacitor: impl AsRef<Path>,
|
||||||
inductor: impl AsRef<Path>,
|
inductor: impl AsRef<Path>,
|
||||||
) -> Result<(), LcrConnError> {
|
) -> Result<(), DatasetError> {
|
||||||
self.resistor.save_file(resistor)?;
|
self.resistor.save_file(resistor)?;
|
||||||
self.capacitor.save_file(capacitor)?;
|
self.capacitor.save_file(capacitor)?;
|
||||||
self.inductor.save_file(inductor)?;
|
self.inductor.save_file(inductor)?;
|
||||||
@@ -329,6 +334,11 @@ impl DatasetCollection {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, TeError)]
|
||||||
|
pub enum ParseHumanReadableValueError {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
/// Convert human readable value to float.
|
/// Convert human readable value to float.
|
||||||
///
|
///
|
||||||
/// # Arguments
|
/// # Arguments
|
||||||
@@ -341,8 +351,8 @@ impl DatasetCollection {
|
|||||||
///
|
///
|
||||||
/// # Errors
|
/// # Errors
|
||||||
///
|
///
|
||||||
/// Returns [`LcrConnError::InvalidHumanReadableValue`] if the input string is not a valid number.
|
/// Returns [`DatasetError::InvalidHumanReadableValue`] if the input string is not a valid number.
|
||||||
pub fn from_human_readable_value(strl: &str) -> Result<f64, LcrConnError> {
|
pub fn from_human_readable_value(strl: &str) -> Result<f64, ParseHumanReadableValueError> {
|
||||||
let strl = strl.trim();
|
let strl = strl.trim();
|
||||||
|
|
||||||
let (num_part, multiplier) = if let Some(stripped) = strl.strip_suffix('n') {
|
let (num_part, multiplier) = if let Some(stripped) = strl.strip_suffix('n') {
|
||||||
@@ -366,7 +376,7 @@ pub fn from_human_readable_value(strl: &str) -> Result<f64, LcrConnError> {
|
|||||||
num_part
|
num_part
|
||||||
.parse::<f64>()
|
.parse::<f64>()
|
||||||
.map(|v| v * multiplier)
|
.map(|v| v * multiplier)
|
||||||
.map_err(|_| LcrConnError::InvalidHumanReadableValue(strl.to_string()))
|
.map_err(|_| DatasetError::InvalidHumanReadableValue(strl.to_string()))
|
||||||
}
|
}
|
||||||
|
|
||||||
/// The unit scale for human readable value.
|
/// The unit scale for human readable value.
|
||||||
|
|||||||
Reference in New Issue
Block a user