use derive_visitor::DriveMut;
use derive_visitor::VisitorMut;
use crate::ast::Expr;
use crate::ast::Identifier;
use crate::ast::Statement;
#[derive(VisitorMut)]
#[visitor(Expr(enter), Identifier(enter))]
pub struct StatementReplacer<F: FnMut(&mut Expr), G: FnMut(&mut Identifier)> {
replace_expr: F,
replace_ident: G,
}
impl<F: FnMut(&mut Expr), G: FnMut(&mut Identifier)> StatementReplacer<F, G> {
pub fn new(replace_expr: F, replace_ident: G) -> Self {
Self {
replace_expr,
replace_ident,
}
}
fn enter_expr(&mut self, expr: &mut Expr) {
(self.replace_expr)(expr);
}
fn enter_identifier(&mut self, ident: &mut Identifier) {
(self.replace_ident)(ident);
}
pub fn visit(&mut self, stmt: &mut Statement) {
stmt.drive_mut(self);
}
}