diff --git a/examples/sequences.rs b/examples/sequences.rs index aada50b..b1f66c7 100644 --- a/examples/sequences.rs +++ b/examples/sequences.rs @@ -158,12 +158,13 @@ fn run(dir: &Path, mode: Mode, create: bool, snapshot: bool, repetitions: usize) let io = Box::new(try!(DiscoverPartitionFiles::from_dir_basename(dir, "seqdb"))); // println!("Discovered: {:?}", *io); - let mut part = if create { - try!(Partition::::create(io, "sequences db")) + let classifier = DummyClassifier::::new(); + let mut repo = if create { + try!(Repo::create(classifier, io, "sequences db")) } else { - let mut part = Partition::::open(io); - try!(part.load(false)); - part + let mut repo = try!(Repo::open(classifier, io)); + try!(repo.load_all(false)); + repo }; let mut rng = rand::thread_rng(); diff --git a/src/detail/classifier.rs b/src/detail/classifier.rs index 74911a1..111b33c 100644 --- a/src/detail/classifier.rs +++ b/src/detail/classifier.rs @@ -55,6 +55,9 @@ pub trait ClassifierT { /// The user-specified element type. type Element: ElementT; + /// Get a reference to the file I/O provider, `RepoIO`. This might be self. + fn io(&self) -> &RepoIO; + /// Initially there should only be one partition and one classification. /// This function gets the number of this classification. /// @@ -182,6 +185,11 @@ pub enum ClassifyFallback { pub struct DummyClassifier { p: PhantomData, } +impl DummyClassifier { + pub fn new() -> DummyClassifier{ + p: PhantomData::new() + } +} impl ClassifierT for DummyClassifier { type Element = E; fn initial(&self) -> PartNum { PartNum::from(1) } diff --git a/src/detail/partition.rs b/src/detail/partition.rs index eecd57a..7924d11 100644 --- a/src/detail/partition.rs +++ b/src/detail/partition.rs @@ -761,6 +761,7 @@ impl Partition { remarks: Vec::new(), user_fields: Vec::new(), }; + //TODO: also write classifier stuff try!(write_head(&header, &mut writer)); try!(write_snapshot(self.states.get(&tip_key).unwrap(), &mut writer)); self.ss_num = ss_num; diff --git a/src/detail/repo.rs b/src/detail/repo.rs index a1cb0be..b5ca74b 100644 --- a/src/detail/repo.rs +++ b/src/detail/repo.rs @@ -2,6 +2,7 @@ use std::slice::{Iter, IterMut}; use std::any::Any; +use std::collections::HashMap; use super::{Partition, PartitionIO, ClassifierT}; use ::error::{Result, OtherError}; @@ -46,9 +47,8 @@ pub struct Repo { io: Box, /// Descriptive identifier for the repository name: String, - /// List of loaded partitions, by in-memory (temporary numeric) identifier. - /// Identifier is TBD (TODO). - partitions: Vec>, + /// List of loaded partitions, by partition number. + partitions: HashMap>, } // Non-member functions on Repo @@ -149,4 +149,27 @@ impl Repo { } all } + + /// Directly insert an element. This uses the classifier to find the + /// relevant partition, get its state, insert there and commit the state. + /// + /// If you know which is the right partition and already have access to its + /// latest state it may be better to insert there. + /// + /// If you plan to make many edits, there should be a more efficient interface .... TODO + pub fn new_elt(&mut self, elt: C::Element) -> Result<(), ElementOp> { + let num = if let Some(num) = self.classifier.classify(&elt) { + num + } else { + match self.classifier.fallback() { + ClassifyFallback::Default(num) | + ClassifyFallback::ReplacedOrDefault(num) => num, + ClassifyFallback::ReplacedOrFail | ClassifyFallback::Fail { + return Err(...) + } + } + }; + + + } }