started day 18
This commit is contained in:
parent
f0fd87aaf7
commit
8ea4258e60
2 changed files with 103 additions and 0 deletions
|
@ -12,4 +12,8 @@ path = "day16.rs"
|
|||
name = "day17"
|
||||
path = "day17.rs"
|
||||
|
||||
[[bin]]
|
||||
name = "day18"
|
||||
path = "day18.rs"
|
||||
|
||||
[dependencies]
|
||||
|
|
99
2021/rust/day18.rs
Normal file
99
2021/rust/day18.rs
Normal file
|
@ -0,0 +1,99 @@
|
|||
#![warn(clippy::all, clippy::pedantic)]
|
||||
|
||||
mod common;
|
||||
use common::day_input;
|
||||
|
||||
type ChildNode<T> = Box<BinaryTreeNode<T>>;
|
||||
|
||||
#[derive(Debug, std::cmp::PartialEq)]
|
||||
struct BinaryTreeBranch<T> {
|
||||
left: ChildNode<T>,
|
||||
right: ChildNode<T>,
|
||||
}
|
||||
|
||||
#[derive(Debug, std::cmp::PartialEq)]
|
||||
enum BinaryTreeNode<T> {
|
||||
Branch(BinaryTreeBranch<T>),
|
||||
Leaf(T),
|
||||
}
|
||||
|
||||
fn crawl_for<T>(node: &BinaryTreeNode<T>, predicate: fn(&BinaryTreeNode<T>, u64) -> bool, current_depth: u64) -> Option<&BinaryTreeNode<T>> {
|
||||
if predicate(node, current_depth) {
|
||||
Some(node)
|
||||
} else if let BinaryTreeNode::Branch(branch) = node {
|
||||
if let Some(result) = crawl_for(&*branch.left, predicate, current_depth + 1) {
|
||||
Some(result)
|
||||
} else if let Some(result) = crawl_for(&*branch.right, predicate, current_depth + 1) {
|
||||
Some(result)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}
|
||||
|
||||
fn maybe_explode<T: std::fmt::Debug>(tree: &mut BinaryTreeNode<T>) -> bool {
|
||||
if let Some(node_to_explode) = crawl_for(tree, |node, d| {
|
||||
if let BinaryTreeNode::Branch(_) = node {
|
||||
// TODO: must both child nodes be leaves?
|
||||
d >= 3
|
||||
} else {
|
||||
false
|
||||
}
|
||||
}, 0) {
|
||||
// TODO: do explosion
|
||||
println!("{:#?}", node_to_explode);
|
||||
true
|
||||
} else {
|
||||
false
|
||||
}
|
||||
}
|
||||
|
||||
fn parse_binary_tree(s: &str) -> Result<BinaryTreeNode<u64>, &'static str> {
|
||||
let chars = s.chars().peekable();
|
||||
let ch = chars.peek();
|
||||
if let Some(c) = ch {
|
||||
match c {
|
||||
'0'..='9' => Ok(BinaryTreeNode::Leaf(u64::from(*c) - ASCII_0))
|
||||
'[' => {
|
||||
it.next()
|
||||
parse_binary_tree(
|
||||
// TODO: parse left piece
|
||||
// TODO: parse right piece
|
||||
// do_parse_binary_tree(&s[1..], depth + 1)
|
||||
// TODO: parse end of this (']')
|
||||
}
|
||||
_ => Err("unknown char")
|
||||
}
|
||||
} else {
|
||||
Err("empty string")
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let result = parse_binary_tree(&day_input(18));
|
||||
println!("Snailfish Homework: {:#?}", result);
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn parser() {
|
||||
assert_eq!(parse_binary_tree("y"), Err("unknown char"));
|
||||
assert_eq!(parse_binary_tree("9"), Ok(BinaryTreeNode::Leaf(9)));
|
||||
assert_eq!(parse_binary_tree("[[1,2],3]"), Ok(BinaryTreeNode::Branch(BinaryTreeBranch {
|
||||
left: Box::new(BinaryTreeNode::Branch(BinaryTreeBranch {
|
||||
left: Box::new(BinaryTreeNode::Leaf(1)),
|
||||
right: Box::new(BinaryTreeNode::Leaf(2)),
|
||||
})),
|
||||
right: Box::new(BinaryTreeNode::Leaf(3)),
|
||||
})));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn needs_exploding() {
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue