aboutsummaryrefslogtreecommitdiff
path: root/src/day3.rs
diff options
context:
space:
mode:
authorAndreas Grois <andi@grois.info>2021-12-04 21:27:32 +0100
committerAndreas Grois <andi@grois.info>2021-12-04 21:40:15 +0100
commit1fef1d907fd313c94904a08f2a5c7fc158550a50 (patch)
treebd3fd3202bfada65dac018f4aabd8b52cf26656c /src/day3.rs
parent236b5298a7ebdfe0f4a7aa41ea45ba577ff45147 (diff)
Remove dependency on unsafe dyn-clone
Diffstat (limited to 'src/day3.rs')
-rw-r--r--src/day3.rs28
1 files changed, 20 insertions, 8 deletions
diff --git a/src/day3.rs b/src/day3.rs
index 81c5977..474eb73 100644
--- a/src/day3.rs
+++ b/src/day3.rs
@@ -1,5 +1,4 @@
use aoc_runner_derive::*;
-use dyn_clone::{clone_trait_object, DynClone};
#[aoc_generator(day3)]
pub fn input_generator<'c>(input : &'c str) -> (Vec<u32>,usize){
@@ -26,9 +25,22 @@ pub fn solve_part1((input,max_len) : &(Vec<u32>,usize)) -> usize {
gamma_rate * epsilon_rate
}
-trait ClonableIterator: Iterator + DynClone {}
-impl<I: Iterator + DynClone> ClonableIterator for I {}
-clone_trait_object!(<T> ClonableIterator<Item = T>);
+trait ClonableIterator<'a>: Iterator<Item = &'a u32> + 'a {
+ fn box_clone(&self) -> Box<dyn ClonableIterator<'a>>;
+}
+
+impl<'a, T: Iterator<Item = &'a u32> + Clone + 'a> ClonableIterator<'a> for T {
+ fn box_clone(&self) -> Box<dyn ClonableIterator<'a>> {
+ Box::new(self.clone())
+ }
+}
+mod helper {
+ impl<'a> Clone for Box<dyn super::ClonableIterator<'a>> {
+ fn clone(&self) -> Self {
+ (*self).box_clone()
+ }
+ }
+}
fn count_ones_and_zeros<'a, T>(iterator : T , bit_from_right : usize) -> (usize, usize)
where T : Iterator<Item=&'a u32>,
@@ -40,21 +52,21 @@ fn has_record_desired_bit(record : u32, most_common_bit_mask : u32, target : u32
(record & most_common_bit_mask) == target
}
-fn find_wanted_rating<'a, T,U>(iterator : T, max_len : usize, comparison : U) -> Option<&'a u32>
+fn find_wanted_rating<'a, T : 'a,U>(iterator : T, max_len : usize, comparison : U) -> Option<&'a u32>
where T : Iterator<Item=&'a u32>+Clone,
U : Fn(usize,usize)->bool
{
use std::ops::ControlFlow as Cf;
- let init : Box<dyn ClonableIterator<Item=&'a u32>> = Box::new(iterator);
+ let init : Box<dyn ClonableIterator<'a>> = Box::new(iterator);
let result = (0..max_len).rev().try_fold(init,|iterator, bit_from_right| {
let mask = 1 << bit_from_right;
- let (ones, zeros) = count_ones_and_zeros(iterator.clone(), bit_from_right);
+ let (ones, zeros) = count_ones_and_zeros((iterator).clone(), bit_from_right);
match ones + zeros {
0 | 1 => { Cf::Break(iterator) }
_ => {
let target_bit_value = if comparison(ones, zeros) { mask } else { 0 };
let filtered = iterator.filter(move |&&value| has_record_desired_bit(value,mask,target_bit_value));
- let boxed : Box<dyn ClonableIterator<Item=&'a u32>> = Box::new(filtered);
+ let boxed : Box<dyn ClonableIterator<'a>> = Box::new(filtered);
Cf::Continue(boxed)
}
}