use crate::input::PrecedenceLevel;
#[derive(Clone, Debug, Default, PartialEq, Eq, Hash, PartialOrd, Ord)]
pub(crate) struct PrecedenceAnnotations {
pub(crate) forbidden_left: Vec<Option<PrecedenceLevel>>,
pub(crate) forbidden_right: Vec<Option<PrecedenceLevel>>,
}
impl PrecedenceAnnotations {
pub(super) const fn new() -> Self {
Self {
forbidden_left: Vec::new(),
forbidden_right: Vec::new(),
}
}
pub(crate) fn is_empty(&self) -> bool {
self.forbidden_left.is_empty() && self.forbidden_right.is_empty()
}
pub(crate) fn compatible_with(
current_precendences: &[Option<PrecedenceLevel>],
next_precendences: &[Option<PrecedenceLevel>],
) -> bool {
for (&level, &next_level) in current_precendences.iter().zip(next_precendences) {
match (level, next_level) {
(Some(level), Some(next_level)) if level > next_level => return false,
_ => {}
}
}
true
}
pub(super) fn merge_increasing(
self_annotations: &mut Vec<Option<PrecedenceLevel>>,
annotations: &[Option<PrecedenceLevel>],
) -> bool {
if self_annotations.len() < annotations.len() {
self_annotations.resize(annotations.len(), None);
}
let mut modified = false;
for (self_level, level) in self_annotations.iter_mut().zip(annotations) {
let level = match *level {
Some(l) => l,
None => continue,
};
match self_level {
Some(l) if *l < level => {
modified = true;
*l = level
}
None => {
modified = true;
*self_level = Some(level)
}
_ => {}
}
}
modified
}
}