pub enum Step<'a, T> {
Success(T, usize),
Fail(usize),
Error(ParseError<'a>),
}
Expand description
The intermediate result for atom parsing
Variants§
Success(T, usize)
Successfully resulted and current position is shifted forward
Fail(usize)
Failed to parse amd current position remains the same
Error(ParseError<'a>)
Unexpected situation pops up (like reached eof or some values can’t pass a validation)
Implementations§
source§impl<'a, L, R> Step<'a, (L, R)>
impl<'a, L, R> Step<'a, (L, R)>
sourcepub fn take_left(self) -> Step<'a, L>
pub fn take_left(self) -> Step<'a, L>
the result if often is a pair of values. This method drops the right side and keeps only left and moves it farther It is used often when there is some token that should present in the particular place but does not carry extra sense like for a signature of a function we need to have brackets.
Example
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
End,
}
enum Word<'a>{ Word(&'a str), Bang(&'a str)}
let pit:Parsit<T> = Parsit::new("word|").unwrap();
let parse = |p:usize|{
token!(pit.token(p) => T::Word(v) => v)
.then_zip(|p| token!(pit.token(p) => T::End))
.take_left()
};
sourcepub fn take_right(self) -> Step<'a, R>
pub fn take_right(self) -> Step<'a, R>
This method is a strict alias for the method then
but for symmetric it presents
source§impl<'a, L> Step<'a, (L, Vec<L>)>
impl<'a, L> Step<'a, (L, Vec<L>)>
sourcepub fn merge(self) -> Step<'a, Vec<L>>
pub fn merge(self) -> Step<'a, Vec<L>>
Mergers the element from the left hand side to the right hand side This case often appears for the situations when there is a head of the same type and the tail that can be optional like
<rule> ::= <value> {"," <value>} // abc, bcd, cde
Here the first value is always presented and the others can be absent.
source§impl<'a, T> Step<'a, T>
impl<'a, T> Step<'a, T>
sourcepub fn then_zip<Res, Then>(self, then: Then) -> Step<'a, (T, Res)>where
Then: FnOnce(usize) -> Step<'a, Res>,
pub fn then_zip<Res, Then>(self, then: Then) -> Step<'a, (T, Res)>where Then: FnOnce(usize) -> Step<'a, Res>,
Takes the next function and if the curren one and the next one are both success transforms the result value into a pair of them
Example
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
Del,
}
let pit:Parsit<T> = Parsit::new("word|another").unwrap();
let word = |p:usize| {token!(pit.token(p) => T::Word(v) => v)};
let del = |p:usize| {token!(pit.token(p) => T::Del)};
let parse = |p:usize|{
word(p)
.then_zip(del)
.take_left()
.then_zip(word)
.map(|(first,second)| format!("{},{}",first,second))
};
sourcepub fn then_skip<Res, Then>(self, then: Then) -> Step<'a, T>where
Then: FnOnce(usize) -> Step<'a, Res>,
pub fn then_skip<Res, Then>(self, then: Then) -> Step<'a, T>where Then: FnOnce(usize) -> Step<'a, Res>,
Drops the next function but keeps the current result. Basically it is an alias for
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
Del,
}
let pit:Parsit<T> = Parsit::new("word|another").unwrap();
let word = |p:usize| {token!(pit.token(p) => T::Word(v) => v)};
let del = |p:usize| {token!(pit.token(p) => T::Del)};
let parse = |p:usize|{
word(p)
.then_skip(del)
.then_zip(word)
.map(|(first,second)| format!("{},{}",first,second))
};
sourcepub fn then_or_val_zip<Res, Then>(
self,
then: Then,
default: Res
) -> Step<'a, (T, Res)>where
Then: FnOnce(usize) -> Step<'a, Res>,
pub fn then_or_val_zip<Res, Then>( self, then: Then, default: Res ) -> Step<'a, (T, Res)>where Then: FnOnce(usize) -> Step<'a, Res>,
Takes the next function and if the curren one and the next one are both success transforms the result value into a pair of them but if the second step is failed(absent) the second value will be replaced with a default value and the step will be succeeded. It is convenient when the second value is optional.
Example
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
Del,
}
enum Word<'a>{ Word(&'a str), Bang(&'a str)}
let pit:Parsit<T> = Parsit::new("word|").unwrap();
let word = |p:usize| {token!(pit.token(p) => T::Word(v) => v)};
let del = |p:usize| {token!(pit.token(p) => T::Del)};
let parse = |p:usize|{
word(p)
.then_zip(del)
.take_left()
.then_or_val_zip(word, &"default")
.map(|(first,second)| format!("{},{}",first,second))
};
sourcepub fn then_or_none_zip<Rhs, Then>(
self,
then: Then
) -> Step<'a, (T, Option<Rhs>)>where
Then: FnOnce(usize) -> Step<'a, Option<Rhs>>,
pub fn then_or_none_zip<Rhs, Then>( self, then: Then ) -> Step<'a, (T, Option<Rhs>)>where Then: FnOnce(usize) -> Step<'a, Option<Rhs>>,
Takes the next function and if the curren one and the next one are both success transforms the result value into a pair of them but if the second step is failed(absent) the second value will be replaced with a none and the step will be succeeded. It is convenient when the second value is optional.
Note : the second result should be an optional in any case
Example
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
Del,
}
let pit:Parsit<T> = Parsit::new("word|").unwrap();
let word = |p:usize| {token!(pit.token(p) => T::Word(v) => v)};
let del = |p:usize| {token!(pit.token(p) => T::Del)};
let parse = |p:usize|{
word(p)
.then_zip(del)
.take_left()
.then_or_none_zip(|p| word(p).or_none()) // here we need to return option
};
sourcepub fn then_or_default_zip<Rhs: Default, Then>(
self,
then: Then
) -> Step<'a, (T, Rhs)>where
Then: FnOnce(usize) -> Step<'a, Rhs>,
pub fn then_or_default_zip<Rhs: Default, Then>( self, then: Then ) -> Step<'a, (T, Rhs)>where Then: FnOnce(usize) -> Step<'a, Rhs>,
Takes the next function and if the curren one and the next one are both success transforms the result value into a pair of them but if the second step is failed(absent) the second value will be replaced with a default variant from the value and the step will be succeeded.
Note : the second result should implement default
Example
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
Del,
}
enum Word<'a>{ Word(&'a str), Bang(&'a str)}
impl<'a> Default for Word<'a>{fn default() -> Self {
Word::Word("")
}}
let pit:Parsit<T> = Parsit::new("word|").unwrap();
let word = |p:usize| {token!(pit.token(p) => T::Word(v) => Word::Word(v))};
let del = |p:usize| {token!(pit.token(p) => T::Del)};
let parse = |p:usize|{
word(p)
.then_zip(del)
.take_left()
.then_or_default_zip(word) // here we return Word("word") and Word("")
};
sourcepub fn then_combine<Rhs, Res, Then, Combine>(
self,
then: Then,
combine: Combine
) -> Step<'a, Res>where
Then: FnOnce(usize) -> Step<'a, Rhs>,
Combine: FnOnce(T, Rhs) -> Res,
pub fn then_combine<Rhs, Res, Then, Combine>( self, then: Then, combine: Combine ) -> Step<'a, Res>where Then: FnOnce(usize) -> Step<'a, Rhs>, Combine: FnOnce(T, Rhs) -> Res,
Combines this step with the next step according to the given function
Arguments
then
- the next function to parsecombine
- the mapper to combine to values
This method is not used a lot directly but turns up as a foundation for others. For examples please see
sourcepub fn then_multi_combine<K, R, Then, Combine>(
self,
then: Then,
combine: Combine
) -> Step<'a, R>where
Then: FnOnce(usize) -> Step<'a, K> + Copy,
Combine: FnOnce(T, Vec<K>) -> R,
pub fn then_multi_combine<K, R, Then, Combine>( self, then: Then, combine: Combine ) -> Step<'a, R>where Then: FnOnce(usize) -> Step<'a, K> + Copy, Combine: FnOnce(T, Vec<K>) -> R,
Applies the given function as many times as it will be succeeded and then combine the result
Please see
sourcepub fn then_multi_zip<R, Then>(self, then: Then) -> Step<'a, (T, Vec<R>)>where
Then: FnOnce(usize) -> Step<'a, R> + Copy,
pub fn then_multi_zip<R, Then>(self, then: Then) -> Step<'a, (T, Vec<R>)>where Then: FnOnce(usize) -> Step<'a, R> + Copy,
Applies the given function as many times as it will be succeeded and then combine the result
into a vec. It is used in the parser in methods zero_or_more
or one_or_more
sourcepub fn then_or_val_combine<Rhs, Res, Then, Combine>(
self,
then: Then,
default: Rhs,
combine: Combine
) -> Step<'a, Res>where
Then: FnOnce(usize) -> Step<'a, Rhs>,
Combine: FnOnce(T, Rhs) -> Res,
pub fn then_or_val_combine<Rhs, Res, Then, Combine>( self, then: Then, default: Rhs, combine: Combine ) -> Step<'a, Res>where Then: FnOnce(usize) -> Step<'a, Rhs>, Combine: FnOnce(T, Rhs) -> Res,
Takes the next function and if the curren one and the next one are both success transforms the result value into a pair of them according to the given function combine
For the details see then_or_val_zip
sourcepub fn then_or_none_combine<Rhs, Res, Then, Combine>(
self,
then: Then,
combine: Combine
) -> Step<'a, Res>where
Then: FnOnce(usize) -> Step<'a, Option<Rhs>>,
Combine: FnOnce(T, Option<Rhs>) -> Res,
pub fn then_or_none_combine<Rhs, Res, Then, Combine>( self, then: Then, combine: Combine ) -> Step<'a, Res>where Then: FnOnce(usize) -> Step<'a, Option<Rhs>>, Combine: FnOnce(T, Option<Rhs>) -> Res,
Takes the next function and if the curren one and the next one are both success transforms the result value into a pair of them according to the given function combine and process the absent value as well
For the details see then_or_none_zip
sourcepub fn then<Rhs, Then>(self, then: Then) -> Step<'a, Rhs>where
Then: FnOnce(usize) -> Step<'a, Rhs>,
pub fn then<Rhs, Then>(self, then: Then) -> Step<'a, Rhs>where Then: FnOnce(usize) -> Step<'a, Rhs>,
Takes and process the next step if the current one is succeed omitting the result of the current step. It is convenient when w need to know only a fact that the parser can parse current token without pulling out extra information from it
Example
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
Del,
}
enum Word<'a>{ Word(&'a str), Bang(&'a str)}
impl<'a> Default for Word<'a>{fn default() -> Self {
Word::Word("")
}}
let pit:Parsit<T> = Parsit::new("|word|").unwrap();
let word = |p:usize| {token!(pit.token(p) => T::Word(v) => Word::Word(v))};
let del = |p:usize| {token!(pit.token(p) => T::Del)};
let parse = |p:usize|{
del(p)
.then(word) // omitting the result of del
.then_zip(del)
.take_left()
};
sourcepub fn then_or_val<Rhs, Then>(self, then: Then, default: Rhs) -> Step<'a, Rhs>where
Then: FnOnce(usize) -> Step<'a, Rhs>,
pub fn then_or_val<Rhs, Then>(self, then: Then, default: Rhs) -> Step<'a, Rhs>where Then: FnOnce(usize) -> Step<'a, Rhs>,
Takes and process the next step if the current one is succeed omitting the result of the current step. It is convenient when w need to know only a fact that the parser can parse current token without pulling out extra information from it
If the next fn is not presented then return a default value
Example
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
Del,
}
enum Word<'a>{ Word(&'a str), Bang(&'a str), EmptyWord}
impl<'a> Default for Word<'a>{fn default() -> Self {
Word::Word("")
}}
let pit:Parsit<T> = Parsit::new("||").unwrap();
let word = |p:usize| {token!(pit.token(p) => T::Word(v) => Word::Word(v))};
let del = |p:usize| {token!(pit.token(p) => T::Del)};
let parse = |p:usize|{
del(p)
.then_or_val(word, Word::EmptyWord) // omitting the result of del and process empty var
.then_zip(del)
.take_left()
};
sourcepub fn then_or_default<Rhs: Default, Then>(self, then: Then) -> Step<'a, Rhs>where
Then: FnOnce(usize) -> Step<'a, Rhs>,
pub fn then_or_default<Rhs: Default, Then>(self, then: Then) -> Step<'a, Rhs>where Then: FnOnce(usize) -> Step<'a, Rhs>,
Takes and process the next step if the current one is succeed omitting the result of the current step. It is convenient when w need to know only a fact that the parser can parse current token without pulling out extra information from it
If the next fn is not presented then return a default value from trait
Example
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
Del,
}
enum Word<'a>{ Word(&'a str), Bang(&'a str), EmptyWord}
impl<'a> Default for Word<'a>{fn default() -> Self {
Word::EmptyWord
}}
let pit:Parsit<T> = Parsit::new("||").unwrap();
let word = |p:usize| {token!(pit.token(p) => T::Word(v) => Word::Word(v))};
let del = |p:usize| {token!(pit.token(p) => T::Del)};
let parse = |p:usize|{
del(p)
.then_or_default(word) // omitting the result of del and process empty var
.then_zip(del)
.take_left()
};
sourcepub fn then_or_none<Rhs, Then>(self, then: Then) -> Step<'a, Option<Rhs>>where
Then: FnOnce(usize) -> Step<'a, Option<Rhs>>,
pub fn then_or_none<Rhs, Then>(self, then: Then) -> Step<'a, Option<Rhs>>where Then: FnOnce(usize) -> Step<'a, Option<Rhs>>,
Takes and process the next step if the current one is succeed omitting the result of the current step. It is convenient when w need to know only a fact that the parser can parse current token without pulling out extra information from it
If the next fn is not presented then return a none
Example
use logos::Logos;
use crate::parsit::token;
use crate::parsit::parser::Parsit;
use crate::parsit::parser::EmptyToken;
use crate::parsit::step::Step;
#[derive(Logos,PartialEq)]
pub enum T<'a> {
#[regex(r"[a-zA-Z-]+")]
Word(&'a str),
#[token("|")]
Del,
}
enum Word<'a>{ Word(&'a str), Bang(&'a str), EmptyWord}
impl<'a> Default for Word<'a>{fn default() -> Self {
Word::Word("")
}}
let pit:Parsit<T> = Parsit::new("||").unwrap();
let word = |p:usize| {token!(pit.token(p) => T::Word(v) => Word::Word(v))};
let del = |p:usize| {token!(pit.token(p) => T::Del)};
let parse = |p:usize|{
del(p)
.then_or_none(|p| word(p).or_none()) // omitting the result of del and process empty var
.then_zip(del)
.take_left()
};
source§impl<'a, T: Debug> Step<'a, T>
impl<'a, T: Debug> Step<'a, T>
sourcepub fn print(self) -> Step<'a, T>
pub fn print(self) -> Step<'a, T>
Prints the information regarding the current step with a prefix The type To should implement debug
Examples
use parsit::step::Step::Success;
let step = Success(vec!["1"],0 );
step.print();
sourcepub fn print_as<Show, To>(self, show: Show) -> Step<'a, T>where
Show: FnOnce(&T) -> &To,
To: Debug,
pub fn print_as<Show, To>(self, show: Show) -> Step<'a, T>where Show: FnOnce(&T) -> &To, To: Debug,
Prints the information regarding the current step transforming the success according to the given function Show
Arguments
show
- function transforming the value into some type that will be printed
The type To should implement debug
Examples
use parsit::step::Step::Success;
let step = Success(vec!["1"],0 );
step.print_as(|v| v.get(0).unwrap());
sourcepub fn print_with(self, prefix: &'a str) -> Step<'a, T>
pub fn print_with(self, prefix: &'a str) -> Step<'a, T>
Prints the information regarding the current step with a prefix
Example
use parsit::step::Step::Success;
let step = Success(1,0);
step
.print_with("some_prefix")
.map(|v| v + 1);
// will be 'some_prefix success, pos: 0, res: 1'
The success type should implement debug trait
sourcepub fn print_with_as<Show, To>(self, prefix: &'a str, show: Show) -> Step<'a, T>where
Show: FnOnce(&T) -> &To,
To: Debug,
pub fn print_with_as<Show, To>(self, prefix: &'a str, show: Show) -> Step<'a, T>where Show: FnOnce(&T) -> &To, To: Debug,
Prints the information regarding the current step with a prefix transforming the success according to the given function Show
Arguments
prefix
- given prefixshow
- function transforming the value into some type that will be printed
The type To should implement debug
Examples
use parsit::step::Step::Success;
let step = Success(vec!["1"],0 );
step.print_with_as("prefix", |v| v.get(0).unwrap());
source§impl<'a, T> Step<'a, T>
impl<'a, T> Step<'a, T>
sourcepub fn map<Rhs, Map>(self, mapper: Map) -> Step<'a, Rhs>where
Map: FnOnce(T) -> Rhs,
pub fn map<Rhs, Map>(self, mapper: Map) -> Step<'a, Rhs>where Map: FnOnce(T) -> Rhs,
Transforms a value if it is success
Examples
use parsit::step::Step;
let step_one = Step::Success(1,0);
let step_two = step_one.map(|v|v + 1);
sourcepub fn flat_map<Rhs, FMap, FMapErr, Err>(
self,
mapper: FMap,
error_map: FMapErr
) -> Step<'a, Rhs>where
FMap: FnOnce(T) -> Result<Rhs, Err>,
FMapErr: FnOnce(Err) -> Step<'a, Rhs>,
pub fn flat_map<Rhs, FMap, FMapErr, Err>( self, mapper: FMap, error_map: FMapErr ) -> Step<'a, Rhs>where FMap: FnOnce(T) -> Result<Rhs, Err>, FMapErr: FnOnce(Err) -> Step<'a, Rhs>,
Transforms a value if it is success into result that can pass father with a transformation to step
Examples
use parsit::error::ParseError;
use parsit::step::Step;
struct Er;
impl<'a> Into<ParseError<'a>> for Er{
fn into(self) -> ParseError<'a> {
ParseError::FinishedOnFail
}}
let step_one = Step::Success(1,0);
let step_two = step_one.flat_map(|v|Ok::<i32,Er>(1 + v), |e| Step::Fail(0));
sourcepub fn combine<Rhs, Res, Combine>(
self,
other: Step<'a, Rhs>,
comb: Combine
) -> Step<'a, Res>where
Combine: FnOnce(T, Rhs) -> Res,
pub fn combine<Rhs, Res, Combine>( self, other: Step<'a, Rhs>, comb: Combine ) -> Step<'a, Res>where Combine: FnOnce(T, Rhs) -> Res,
Combines the results from the current step(success) and with the given step success
Example
use parsit::step::Step;
let step = Step::Success(1,0);
let next = step.combine(Step::Success(1,1),|a,b| a + b);
Notes
- If the result is successfull for both the latter position is taken
- If the result is failed the latest position is taken
- If the result is error the latest error is taken
sourcepub fn validate<Validation>(self, validate: Validation) -> Step<'a, T>where
Validation: FnOnce(&T) -> Result<(), &'a str>,
pub fn validate<Validation>(self, validate: Validation) -> Step<'a, T>where Validation: FnOnce(&T) -> Result<(), &'a str>,
Validates successful result and transforms into error if the validation is failed
Examples
use parsit::error::ParseError;
use parsit::step::Step;
let res = Step::Success("", 1);
let res = res.validate(|v| {
if v.len() > 0 { Ok(()) } else { Err("empty") }
});
if let Some(ParseError::FailedOnValidation(v,_)) = res.error(){
assert_eq!(v, "empty")
} else { assert!(false) };
sourcepub fn error(self) -> Option<ParseError<'a>>
pub fn error(self) -> Option<ParseError<'a>>
Transforms error result into option if it is error or returns None otherwise
Example
use parsit::error::ParseError;
use parsit::step::Step;
let res = Step::Success("", 1);
let res = res.validate(|v| {
if v.len() > 0 { Ok(()) } else { Err("empty") }
});
if let Some(ParseError::FailedOnValidation(v,_)) = res.error(){
assert_eq!(v, "empty")
} else { assert!(false) };
source§impl<'a, T> Step<'a, T>
impl<'a, T> Step<'a, T>
sourcepub fn or_val(self, default: T) -> Step<'a, T>
pub fn or_val(self, default: T) -> Step<'a, T>
Provides a default alternative for the given rule in case if the value does not present.
This is an implementation for or_val that provides a none as a default. It can be used to process an optional values when we have a specific default value to provide
#Example
<rule> ::= "value" ["!"]
use logos::Logos;
use crate::parsit::parser::Parsit;
use crate::parsit::token;
use crate::parsit::step::Step;
use crate::parsit::parser::EmptyToken;
#[derive(Logos,PartialEq)]
pub enum T {
#[token("value")]
Value,
#[token("!")]
Bang,
}
struct Value(bool);
let p:Parsit<T> = Parsit::new("value").unwrap();
let bang_opt = |pos| {
token!(p.token(pos) => T::Bang => true).or_val(false)
};
let parse =
token!(p.token(0) => T::Value)
.then_zip(bang_opt)
.take_right()
.map(Value);
sourcepub fn or_none(self) -> Step<'a, Option<T>>
pub fn or_none(self) -> Step<'a, Option<T>>
Provides an optional alternative for the given rule in case if the value does not present
This is an implementation for or_val that provides a none as a default. It can be used to process an optional values
#Example
use logos::Logos;
use crate::parsit::parser::Parsit;
use crate::parsit::token;
use crate::parsit::step::Step;
use crate::parsit::parser::EmptyToken;
#[derive(Logos,PartialEq)]
pub enum T {
#[token("value")]
Value,
#[token("!")]
Bang,
}
struct Value(bool);
let p:Parsit<T> = Parsit::new("value").unwrap();
let bang_opt = |pos| {
token!(p.token(pos) => T::Bang).or_none()
};
let parse =
token!(p.token(0) => T::Value)
.then_zip(bang_opt)
.take_right()
.map(|opt| Value(opt.is_some()) );
sourcepub fn or<Alt>(self, next: Alt) -> Step<'a, T>where
Alt: FnOnce(usize) -> Step<'a, T>,
pub fn or<Alt>(self, next: Alt) -> Step<'a, T>where Alt: FnOnce(usize) -> Step<'a, T>,
Provides a function of backtracking in a horizon of one token. It works for non complex rules or for the rules that have a distinction in the beginning of parsing like
f: '[' items ']';
s: '(' items ')';
t: '{' items '}';
rule: f | s | t ;
Example
let first = |p|{ token!(token => LBracket).then(items) };
let second = |p|{ token!(token => LParen).then(items) };
let third = |p|{ token!(token => LSquare).then(items) };
first(pos)
.or(second)
.or(third)