Adding example for readonly

This commit is contained in:
vandomej 2021-08-26 15:08:40 -07:00
parent bd57448f56
commit 94dbcd1f3a
2 changed files with 71 additions and 23 deletions

View file

@ -33,7 +33,7 @@ use std::string::ToString;
/// # type Err = String; /// # type Err = String;
/// # /// #
/// # fn from_str(s: &str) -> Result<TestState, Self::Err> { /// # fn from_str(s: &str) -> Result<TestState, Self::Err> {
/// # toml::from_str(s).map_err(|_| format!("Unable to parse string {}", s)) /// # serde_json::from_str(s).map_err(|_| format!("Unable to parse string {}", s))
/// # } /// # }
/// # } /// # }
/// # /// #
@ -150,7 +150,7 @@ where
+ Clone, + Clone,
{ {
/// Initializes a bracket of type `T` storing the contents to `file_path` /// Initializes a bracket of type `T` storing the contents to `file_path`
/// ///
/// # Examples /// # Examples
/// ``` /// ```
/// # use gemla::bracket::*; /// # use gemla::bracket::*;
@ -169,7 +169,7 @@ where
/// # type Err = String; /// # type Err = String;
/// # /// #
/// # fn from_str(s: &str) -> Result<TestState, Self::Err> { /// # fn from_str(s: &str) -> Result<TestState, Self::Err> {
/// # toml::from_str(s).map_err(|_| format!("Unable to parse string {}", s)) /// # serde_json::from_str(s).map_err(|_| format!("Unable to parse string {}", s))
/// # } /// # }
/// # } /// # }
/// # /// #
@ -206,17 +206,17 @@ where
/// fn initialize() -> Result<Box<Self>, String> { /// fn initialize() -> Result<Box<Self>, String> {
/// Ok(Box::new(TestState { score: 0.0 })) /// Ok(Box::new(TestState { score: 0.0 }))
/// } /// }
/// ///
/// //... /// //...
/// } /// }
/// ///
/// # fn main() { /// # fn main() {
/// let mut bracket = Bracket::<TestState>::initialize("./temp".to_string()) /// let mut bracket = Bracket::<TestState>::initialize("./temp".to_string())
/// .expect("Bracket failed to initialize"); /// .expect("Bracket failed to initialize");
/// ///
/// assert_eq!( /// assert_eq!(
/// format!("{}", bracket), /// format!("{}", bracket),
/// format!("{{\"tree\":{},\"iteration_scaling\":{{\"enumType\":\"Constant\",\"enumContent\":1}}}}", /// format!("{{\"tree\":{},\"iteration_scaling\":{{\"enumType\":\"Constant\",\"enumContent\":1}}}}",
/// btree!(TestState::new(0.0))) /// btree!(TestState::new(0.0)))
/// ); /// );
/// ///
@ -234,7 +234,7 @@ where
} }
/// Given a bracket object, configures it's [`IterationScaling`]. /// Given a bracket object, configures it's [`IterationScaling`].
/// ///
/// # Examples /// # Examples
/// ``` /// ```
/// # use gemla::bracket::*; /// # use gemla::bracket::*;
@ -252,7 +252,7 @@ where
/// # type Err = String; /// # type Err = String;
/// # /// #
/// # fn from_str(s: &str) -> Result<TestState, Self::Err> { /// # fn from_str(s: &str) -> Result<TestState, Self::Err> {
/// # toml::from_str(s).map_err(|_| format!("Unable to parse string {}", s)) /// # serde_json::from_str(s).map_err(|_| format!("Unable to parse string {}", s))
/// # } /// # }
/// # } /// # }
/// # /// #
@ -342,8 +342,8 @@ where
/// 1) Creating a new branch of the same height and performing the same steps for each subtree. /// 1) Creating a new branch of the same height and performing the same steps for each subtree.
/// 2) Simulating the top node of the current branch. /// 2) Simulating the top node of the current branch.
/// 3) Comparing the top node of the current branch to the top node of the new branch. /// 3) Comparing the top node of the current branch to the top node of the new branch.
/// 4) Takes the best performing node and makes it the root of the tree. /// 4) Takes the best performing node and makes it the root of the tree.
/// ///
/// # Examples /// # Examples
/// ``` /// ```
/// # use gemla::bracket::*; /// # use gemla::bracket::*;
@ -361,7 +361,7 @@ where
/// # type Err = String; /// # type Err = String;
/// # /// #
/// # fn from_str(s: &str) -> Result<TestState, Self::Err> { /// # fn from_str(s: &str) -> Result<TestState, Self::Err> {
/// # toml::from_str(s).map_err(|_| format!("Unable to parse string {}", s)) /// # serde_json::from_str(s).map_err(|_| format!("Unable to parse string {}", s))
/// # } /// # }
/// # } /// # }
/// # /// #
@ -403,16 +403,16 @@ where
/// # fn main() { /// # fn main() {
/// let mut bracket = Bracket::<TestState>::initialize("./temp".to_string()) /// let mut bracket = Bracket::<TestState>::initialize("./temp".to_string())
/// .expect("Bracket failed to initialize"); /// .expect("Bracket failed to initialize");
/// ///
/// // Running simulations 3 times /// // Running simulations 3 times
/// for _ in 0..3 { /// for _ in 0..3 {
/// bracket /// bracket
/// .mutate(|b| drop(b.run_simulation_step())) /// .mutate(|b| drop(b.run_simulation_step()))
/// .expect("Failed to run step"); /// .expect("Failed to run step");
/// } /// }
/// ///
/// assert_eq!(bracket.readonly().tree.height(), 4); /// assert_eq!(bracket.readonly().tree.height(), 4);
/// ///
/// # std::fs::remove_file("./temp").expect("Unable to remove file"); /// # std::fs::remove_file("./temp").expect("Unable to remove file");
/// # } /// # }
/// ``` /// ```
@ -454,7 +454,7 @@ mod tests {
type Err = String; type Err = String;
fn from_str(s: &str) -> Result<TestState, Self::Err> { fn from_str(s: &str) -> Result<TestState, Self::Err> {
toml::from_str(s).map_err(|_| format!("Unable to parse string {}", s)) serde_json::from_str(s).map_err(|_| format!("Unable to parse string {}", s))
} }
} }

View file

@ -1,3 +1,5 @@
//! A wrapper around an object that ties it to a physical file
use std::fmt; use std::fmt;
use std::fs; use std::fs;
use std::io::Read; use std::io::Read;
@ -6,21 +8,64 @@ use std::str::FromStr;
use std::string::String; use std::string::String;
use std::string::ToString; use std::string::ToString;
pub struct FileLinked<T> { /// A wrapper around an object `T` that ties the object to a physical file
pub struct FileLinked<T>
where
T: ToString,
{
val: T, val: T,
path: String, path: String,
} }
impl<T> FileLinked<T> {
pub fn readonly(&self) -> &T {
&self.val
}
}
impl<T> FileLinked<T> impl<T> FileLinked<T>
where where
T: ToString, T: ToString,
{ {
/// Returns a readonly reference of `T`
///
/// # Examples
/// ```
/// # use gemla::file_linked::*;
/// # use serde::{Deserialize, Serialize};
/// # use std::fmt;
/// # use std::string::ToString;
/// #
/// #[derive(Deserialize, Serialize)]
/// struct Test {
/// pub a: u32,
/// pub b: String,
/// pub c: f64
/// }
///
/// impl ToString for Test {
/// fn to_string(&self) -> String {
/// serde_json::to_string(self)
/// .expect("unable to deserialize")
/// }
/// }
///
/// # fn main() {
/// let test = Test {
/// a: 1,
/// b: String::from("two"),
/// c: 3.0
/// };
///
/// let linked_test = FileLinked::new(test, String::from("./temp"))
/// .expect("Unable to create file linked object");
///
/// assert_eq!(linked_test.readonly().a, 1);
/// assert_eq!(linked_test.readonly().b, String::from("two"));
/// assert_eq!(linked_test.readonly().c, 3.0);
/// #
/// # std::fs::remove_file("./temp").expect("Unable to remove file");
/// # }
/// ```
pub fn readonly(&self) -> &T {
&self.val
}
/// Creates a new [`FileLinked`] object of type `T` stored to the file given by `path`.
pub fn new(val: T, path: String) -> Result<FileLinked<T>, String> { pub fn new(val: T, path: String) -> Result<FileLinked<T>, String> {
let result = FileLinked { val, path }; let result = FileLinked { val, path };
@ -98,7 +143,10 @@ where
} }
} }
impl<T: fmt::Display> fmt::Display for FileLinked<T> { impl<T: fmt::Display> fmt::Display for FileLinked<T>
where
T: ToString,
{
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "{}", self.val) write!(f, "{}", self.val)
} }