Skip to content

Commit

Permalink
feat: add Biplate::with_children_bi
Browse files Browse the repository at this point in the history
Add Biplate::with_children_bi method. This is identical to
Uniplate::with_children, but for a Biplate.

Fixes: #25
  • Loading branch information
niklasdewally committed Nov 26, 2024
1 parent 8ded20b commit 543f4d5
Show file tree
Hide file tree
Showing 2 changed files with 31 additions and 0 deletions.
21 changes: 21 additions & 0 deletions uniplate/src/traits.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,27 @@ where
/// If from == to then this function should return the root as the single child.
fn biplate(&self) -> (Tree<To>, Box<dyn Fn(Tree<To>) -> Self>);

/// Reconstructs the node with the given children.
///
/// # Panics
///
/// If there are a different number of children given as there were originally returned by
/// children().
fn with_children_bi(&self, children: im::Vector<To>) -> Self {
// 1. Turn old tree into list.
// 2. Check lists are same size.
// 3. Use the reconstruction function given by old_children.list() to
// create a tree with the same structure but the new lists' elements .

let (old_children, ctx) = self.biplate();
let (old_children_lst, rebuild) = old_children.list();
if old_children_lst.len() != children.len() {
panic!("with_children() given an unexpected amount of children");
} else {
ctx(rebuild(children))
}
}

/// Like descend but with more general types.
///
/// If from == to then this function does not descend. Therefore, when writing definitions it
Expand Down
10 changes: 10 additions & 0 deletions uniplate/tests/derive-pass/biplate-stmt.rs
Original file line number Diff line number Diff line change
Expand Up @@ -40,4 +40,14 @@ pub fn main() {
assert_eq!(strings_in_stmt_1.len(), 2);
assert!(strings_in_stmt_1.contains(&"x".into()));
assert!(strings_in_stmt_1.contains(&"y".into()));

// same type property
let children = <Stmt as Biplate<Stmt>>::children_bi(&stmt_1);
assert_eq!(children.len(),1);
assert_eq!(children[0],stmt_1);

// test with_children_bi
let children = <Stmt as Biplate<String>>::children_bi(&stmt_1);
let reconstructed = <Stmt as Biplate<String>>::with_children_bi(&stmt_1,children);
assert_eq!(reconstructed,stmt_1);
}

0 comments on commit 543f4d5

Please sign in to comment.