#[derive(Debug)]
pub struct Params<'c, 'm> {
captures: &'c mut [Slot],
matches: &'m mut [bool],
matched_any: bool,
match_short: bool,
}
pub type Slot = Option<usize>;
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub enum MatchStyle {
Short,
All,
Find,
Capture,
}
impl MatchStyle {
pub fn match_only(&self) -> bool {
match *self {
MatchStyle::Short | MatchStyle::All => true,
_ => false,
}
}
pub fn quit_after_first_match(&self) -> bool {
*self == MatchStyle::Short
}
}
impl<'c, 'm> Params<'c, 'm> {
pub fn new(caps: &'c mut [Slot], mats: &'m mut [bool]) -> Params<'c, 'm> {
Params {
captures: caps,
matches: mats,
matched_any: false,
match_short: false,
}
}
pub fn reset(&mut self) {
for slot in self.captures.iter_mut() {
*slot = None;
}
for m in self.matches.iter_mut() {
*m = false;
}
}
pub fn set_match_short(mut self, yes: bool) -> Params<'c, 'm> {
self.match_short = yes;
self
}
pub fn alloc_captures(n: usize) -> Vec<Slot> {
vec![None; 2 * n]
}
pub fn alloc_matches(n: usize) -> Vec<bool> {
vec![false; n]
}
pub fn captures(&self) -> &[Slot] {
&self.captures
}
pub fn captures_mut(&mut self) -> &mut [Slot] {
&mut self.captures
}
pub fn is_match(&self) -> bool {
self.matched_any
}
pub fn matches(&self) -> &[bool] {
&self.matches
}
#[doc(hidden)]
pub fn set_capture(&mut self, i: usize, slot: Slot) {
if let Some(old_slot) = self.captures.get_mut(i) {
*old_slot = slot;
}
}
#[doc(hidden)]
pub fn set_start(&mut self, slot: Slot) {
self.set_capture(0, slot)
}
#[doc(hidden)]
pub fn set_end(&mut self, slot: Slot) {
self.set_capture(1, slot)
}
#[doc(hidden)]
pub fn copy_captures_from(&mut self, caps: &[Slot]) {
for (slot, val) in self.captures.iter_mut().zip(caps.iter()) {
*slot = *val;
}
}
#[doc(hidden)]
pub fn set_match(&mut self, i: usize) {
self.matched_any = true;
if let Some(old) = self.matches.get_mut(i) {
*old = true;
}
}
#[doc(hidden)]
pub fn style(&self) -> MatchStyle {
if self.match_short {
MatchStyle::Short
} else if self.captures.is_empty() {
if self.matches.len() > 1 {
MatchStyle::All
} else {
MatchStyle::Short
}
} else if self.captures.len() > 2 {
MatchStyle::Capture
} else {
MatchStyle::Find
}
}
}