Implement iterator for context.
This commit is contained in:
16
src/context/global_settings.rs
Normal file
16
src/context/global_settings.rs
Normal file
@@ -0,0 +1,16 @@
|
||||
#[derive(Debug)]
|
||||
pub struct GlobalSettings<'s> {
|
||||
placeholder: Option<&'s str>,
|
||||
}
|
||||
|
||||
impl<'s> GlobalSettings<'s> {
|
||||
pub fn new() -> Self {
|
||||
GlobalSettings { placeholder: None }
|
||||
}
|
||||
}
|
||||
|
||||
impl<'s> Default for GlobalSettings<'s> {
|
||||
fn default() -> Self {
|
||||
GlobalSettings::new()
|
||||
}
|
||||
}
|
||||
@@ -27,6 +27,10 @@ impl<'parent, T> List<'parent, T> {
|
||||
pub fn iter(&self) -> Iter<'_, T> {
|
||||
Iter { next: Some(self) }
|
||||
}
|
||||
|
||||
pub fn iter_list(&self) -> IterList<'_, T> {
|
||||
Iter { next: Some(self) }
|
||||
}
|
||||
}
|
||||
|
||||
pub trait ListType<'parent, T> {
|
||||
@@ -64,3 +68,17 @@ impl<'a, T> Iterator for Iter<'a, T> {
|
||||
ret
|
||||
}
|
||||
}
|
||||
|
||||
pub struct IterList<'a, T> {
|
||||
next: Link<'a, T>,
|
||||
}
|
||||
|
||||
impl<'a, T> Iterator for IterList<'a, T> {
|
||||
type Item = &'a List<'a, T>;
|
||||
|
||||
fn next(&mut self) -> Option<Self::Item> {
|
||||
let ret = self.next;
|
||||
self.next = self.next.map(|this| this.get_parent()).flatten();
|
||||
ret
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,6 +3,7 @@ use crate::error::Res;
|
||||
use crate::parser::OrgSource;
|
||||
|
||||
mod exiting;
|
||||
mod global_settings;
|
||||
mod list;
|
||||
mod parser_context;
|
||||
mod parser_with_context;
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
use nom::combinator::eof;
|
||||
|
||||
use super::exiting::ExitClass;
|
||||
use super::global_settings::GlobalSettings;
|
||||
use super::list::List;
|
||||
use super::DynContextMatcher;
|
||||
use crate::error::Res;
|
||||
@@ -128,33 +129,16 @@ impl<'r> std::fmt::Debug for ExitMatcherNode<'r> {
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct GlobalSettings<'s> {
|
||||
placeholder: Option<&'s str>,
|
||||
}
|
||||
|
||||
impl<'s> GlobalSettings<'s> {
|
||||
pub fn new() -> Self {
|
||||
GlobalSettings { placeholder: None }
|
||||
}
|
||||
}
|
||||
|
||||
impl<'s> Default for GlobalSettings<'s> {
|
||||
fn default() -> Self {
|
||||
GlobalSettings::new()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct Context<'r, 's> {
|
||||
global_settings: &'s GlobalSettings<'s>,
|
||||
tree: List<'r, ContextElement<'r, 's>>,
|
||||
tree: &'r List<'r, ContextElement<'r, 's>>,
|
||||
}
|
||||
|
||||
impl<'r, 's> Context<'r, 's> {
|
||||
pub fn new(
|
||||
global_settings: &'s GlobalSettings<'s>,
|
||||
tree: List<'r, ContextElement<'r, 's>>,
|
||||
tree: &'r List<'r, ContextElement<'r, 's>>,
|
||||
) -> Self {
|
||||
Self {
|
||||
global_settings,
|
||||
@@ -162,16 +146,6 @@ impl<'r, 's> Context<'r, 's> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn document_context(global_settings: &'s GlobalSettings<'s>) -> Self {
|
||||
Context::new(
|
||||
global_settings,
|
||||
List::new(ContextElement::ExitMatcherNode(ExitMatcherNode {
|
||||
exit_matcher: &document_end,
|
||||
class: ExitClass::Document,
|
||||
})),
|
||||
)
|
||||
}
|
||||
|
||||
pub fn with_additional_node(&self, data: ContextElement<'r, 's>) -> Self {
|
||||
let new_tree = self.tree.push(data);
|
||||
Self {
|
||||
@@ -179,6 +153,24 @@ impl<'r, 's> Context<'r, 's> {
|
||||
tree: new_tree,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn iter(&self) -> super::list::Iter<'r, ContextElement<'r, 's>> {
|
||||
self.tree.iter()
|
||||
}
|
||||
|
||||
pub fn iter_context(&self) -> Iter<'r, 's> {
|
||||
Iter {
|
||||
next: self.tree.iter_list(),
|
||||
global_settings: self.global_settings,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_parent(&self) -> Option<Self> {
|
||||
self.tree.get_parent().map(|parent_tree| Self {
|
||||
global_settings: self.global_settings,
|
||||
tree: parent_tree,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg_attr(feature = "tracing", tracing::instrument(ret, level = "debug"))]
|
||||
@@ -188,3 +180,27 @@ fn document_end<'r, 's>(
|
||||
) -> Res<OrgSource<'s>, OrgSource<'s>> {
|
||||
eof(input)
|
||||
}
|
||||
|
||||
pub struct Iter<'r, 's> {
|
||||
global_settings: &'s GlobalSettings<'s>,
|
||||
next: super::list::IterList<'r, ContextElement<'r, 's>>,
|
||||
}
|
||||
|
||||
impl<'r, 's> Iterator for Iter<'r, 's> {
|
||||
type Item = Context<'r, 's>;
|
||||
|
||||
fn next(&mut self) -> Option<Self::Item> {
|
||||
let next_tree = self.next.next();
|
||||
let ret = next_tree.map(|parent_tree| Context::new(self.global_settings, parent_tree));
|
||||
ret
|
||||
}
|
||||
}
|
||||
|
||||
impl<'r, 's> ContextElement<'r, 's> {
|
||||
pub fn document_context() -> Self {
|
||||
Self::ExitMatcherNode(ExitMatcherNode {
|
||||
exit_matcher: &document_end,
|
||||
class: ExitClass::Document,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user