Compare commits
2 Commits
9ef7abed94
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
| 71db768227 | |||
| 26d64ba4c9 |
@@ -47,6 +47,9 @@ path = "src/day10/main.rs"
|
|||||||
name = "day11"
|
name = "day11"
|
||||||
path = "src/day11/main.rs"
|
path = "src/day11/main.rs"
|
||||||
|
|
||||||
|
[[bin]]
|
||||||
|
name = "day12"
|
||||||
|
path = "src/day12/main.rs"
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
anyhow = "1.0.100"
|
anyhow = "1.0.100"
|
||||||
|
|||||||
22
a
Normal file
22
a
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
Found Valid ans 0
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Could not Find valid answer 1
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Could not Find valid answer 2
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
sol1: 1
|
||||||
@@ -1,11 +1,10 @@
|
|||||||
use anyhow::{Ok, Result};
|
use anyhow::{Ok, Result};
|
||||||
use core::panic;
|
use core::panic;
|
||||||
use rand::seq::{IteratorRandom, SliceRandom};
|
use rand::seq::SliceRandom;
|
||||||
use std::{
|
use std::{
|
||||||
collections::{HashMap, HashSet, VecDeque},
|
collections::{HashMap, HashSet, VecDeque},
|
||||||
fmt::Debug,
|
fmt::Debug,
|
||||||
fs,
|
fs,
|
||||||
io::{self, prelude::*},
|
|
||||||
ops::RangeInclusive,
|
ops::RangeInclusive,
|
||||||
u64, vec,
|
u64, vec,
|
||||||
};
|
};
|
||||||
@@ -292,7 +291,6 @@ impl Simplyfy for Vec<EqPart> {
|
|||||||
trait EqSystem {
|
trait EqSystem {
|
||||||
fn cleanup(&mut self) -> Option<u64>;
|
fn cleanup(&mut self) -> Option<u64>;
|
||||||
fn cleanup_quiet(&mut self, allow_vars: bool) -> Option<u64>;
|
fn cleanup_quiet(&mut self, allow_vars: bool) -> Option<u64>;
|
||||||
fn apply(&mut self, var: u64, replc: Vec<EqPart>) -> &mut Self;
|
|
||||||
fn apply_num(&mut self, var: u64, replc: i64) -> &mut Self;
|
fn apply_num(&mut self, var: u64, replc: i64) -> &mut Self;
|
||||||
// Return true if success
|
// Return true if success
|
||||||
fn find_1_coe_on_other_side_and_swap(&mut self, k: EqPart) -> bool;
|
fn find_1_coe_on_other_side_and_swap(&mut self, k: EqPart) -> bool;
|
||||||
@@ -304,10 +302,12 @@ impl EqSystem for HashMap<EqPart, Vec<EqPart>> {
|
|||||||
let mut new_values = 0;
|
let mut new_values = 0;
|
||||||
let mut to_delete = Vec::new();
|
let mut to_delete = Vec::new();
|
||||||
for (k, v) in self.iter() {
|
for (k, v) in self.iter() {
|
||||||
println!("{:?} = {:?}", k, v);
|
|
||||||
let idx = match k {
|
let idx = match k {
|
||||||
EqPart::Var(idx, _) => idx,
|
EqPart::Var(idx, _) => idx,
|
||||||
_ => continue,
|
_ => {
|
||||||
|
println!("{:?} = {:?}", k, v);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
if v.len() == 1 {
|
if v.len() == 1 {
|
||||||
if let EqPart::Num(v) = v[0] {
|
if let EqPart::Num(v) = v[0] {
|
||||||
@@ -315,18 +315,19 @@ impl EqSystem for HashMap<EqPart, Vec<EqPart>> {
|
|||||||
println!("\t Invalid state {}! applying", idx);
|
println!("\t Invalid state {}! applying", idx);
|
||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
println!("\t Found part sol for {}! applying", idx);
|
|
||||||
to_delete.push(*k);
|
to_delete.push(*k);
|
||||||
new_values += v as u64;
|
new_values += v as u64;
|
||||||
}
|
}
|
||||||
} else if v.len() == 0 {
|
} else if v.len() == 0 {
|
||||||
println!("\t Found part sol for {} it's 0!", idx);
|
|
||||||
to_delete.push(*k);
|
to_delete.push(*k);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
print!("Found: ");
|
||||||
for i in to_delete {
|
for i in to_delete {
|
||||||
self.remove(&i);
|
let r = self.remove(&i);
|
||||||
|
print!("{:?} {:?} ", i, r.unwrap());
|
||||||
}
|
}
|
||||||
|
print!("\n");
|
||||||
return Some(new_values);
|
return Some(new_values);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -334,7 +335,7 @@ impl EqSystem for HashMap<EqPart, Vec<EqPart>> {
|
|||||||
let mut new_values = 0;
|
let mut new_values = 0;
|
||||||
let mut to_delete = Vec::new();
|
let mut to_delete = Vec::new();
|
||||||
for (k, v) in self.iter() {
|
for (k, v) in self.iter() {
|
||||||
let idx = match k {
|
let _ = match k {
|
||||||
EqPart::Var(idx, _) => idx,
|
EqPart::Var(idx, _) => idx,
|
||||||
EqPart::Num(n) => {
|
EqPart::Num(n) => {
|
||||||
if allow_vars {
|
if allow_vars {
|
||||||
@@ -368,13 +369,6 @@ impl EqSystem for HashMap<EqPart, Vec<EqPart>> {
|
|||||||
return Some(new_values);
|
return Some(new_values);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn apply(&mut self, var: u64, replc: Vec<EqPart>) -> &mut Self {
|
|
||||||
for v in self.values_mut() {
|
|
||||||
v.smart_insert(EqPart::Var(var, 1), replc.clone());
|
|
||||||
}
|
|
||||||
self
|
|
||||||
}
|
|
||||||
|
|
||||||
fn apply_num(&mut self, var: u64, replc: i64) -> &mut Self {
|
fn apply_num(&mut self, var: u64, replc: i64) -> &mut Self {
|
||||||
for v in self.values_mut() {
|
for v in self.values_mut() {
|
||||||
if replc == 0 {
|
if replc == 0 {
|
||||||
@@ -517,34 +511,6 @@ impl EqSystem for HashMap<EqPart, Vec<EqPart>> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_presses_for_m(target: &Vec<u64>, buttons: &Vec<Vec<u64>>, i: usize) -> Option<u64> {
|
|
||||||
if i >= buttons.len() {
|
|
||||||
return None;
|
|
||||||
}
|
|
||||||
let button: &Vec<u64> = buttons[i].as_ref();
|
|
||||||
|
|
||||||
let max_can_add = button
|
|
||||||
.iter()
|
|
||||||
.fold(u64::MAX, |m, i| m.min(target[*i as usize]));
|
|
||||||
if max_can_add == 0 {
|
|
||||||
return get_presses_for_m(target, &buttons, i + 1);
|
|
||||||
}
|
|
||||||
for to_remove in (0..=max_can_add).rev() {
|
|
||||||
let mut n_target = target.clone();
|
|
||||||
for i in button.iter() {
|
|
||||||
n_target[*i as usize] -= to_remove;
|
|
||||||
}
|
|
||||||
// println!("max {:?}: {} - {:?}", button, to_remove, n_target);
|
|
||||||
if n_target.iter().all(|a| *a == 0) {
|
|
||||||
return Some(to_remove);
|
|
||||||
}
|
|
||||||
if let Some(v) = get_presses_for_m(&n_target, &buttons, i + 1) {
|
|
||||||
return Some(to_remove + v);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return None;
|
|
||||||
}
|
|
||||||
|
|
||||||
fn main() -> Result<()> {
|
fn main() -> Result<()> {
|
||||||
let text = fs::read_to_string("src/day10/act.txt")?;
|
let text = fs::read_to_string("src/day10/act.txt")?;
|
||||||
|
|
||||||
@@ -698,221 +664,215 @@ fn main() -> Result<()> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// if try_later.len() >= 1 {
|
if try_later.len() >= 1 {
|
||||||
// fn try_later_mult(
|
fn try_later_mult(
|
||||||
// hash_t: &mut HashMap<EqPart, Vec<EqPart>>,
|
hash_t: &mut HashMap<EqPart, Vec<EqPart>>,
|
||||||
// machine: &Machine,
|
machine: &Machine,
|
||||||
// try_later: Vec<usize>,
|
try_later: Vec<usize>,
|
||||||
// ) -> (u64, Vec<usize>) {
|
) -> (u64, Vec<usize>) {
|
||||||
// let mut sol2 = hash_t.cleanup().unwrap();
|
let mut sol2 = hash_t.cleanup().unwrap();
|
||||||
|
|
||||||
// println!("Something failed to get need to try later");
|
println!("Something failed to get need to try later");
|
||||||
// for (k, v) in hash_t.iter() {
|
for (k, v) in hash_t.iter() {
|
||||||
// println!("{:?} = {:?}", k, v)
|
println!("{:?} = {:?}", k, v)
|
||||||
// }
|
}
|
||||||
|
|
||||||
// let mut try_later_2 = Vec::new();
|
let mut try_later_2 = Vec::new();
|
||||||
// 'try_later: for i in try_later {
|
'try_later: for i in try_later {
|
||||||
// // Get the one based on the index
|
// Get the one based on the index
|
||||||
// let cur_options = hash_t.remove(&EqPart::Index(i)).unwrap();
|
let cur_options = hash_t.remove(&EqPart::Index(i)).unwrap();
|
||||||
// // Insert the actual value one
|
// Insert the actual value one
|
||||||
// let k = EqPart::Num(machine.req[i] as i64);
|
let k = EqPart::Num(machine.req[i] as i64);
|
||||||
// hash_t.insert(k, cur_options);
|
hash_t.insert(k, cur_options);
|
||||||
|
|
||||||
// if !hash_t.find_1_coe_on_other_side_and_swap(k) {
|
if !hash_t.find_1_coe_on_other_side_and_swap(k) {
|
||||||
// // removed value based one not to screw with next step
|
// removed value based one not to screw with next step
|
||||||
// let cur_options = hash_t.remove(&k).unwrap();
|
let cur_options = hash_t.remove(&k).unwrap();
|
||||||
// hash_t.insert(EqPart::Index(i), cur_options.clone());
|
hash_t.insert(EqPart::Index(i), cur_options.clone());
|
||||||
|
|
||||||
// // Ok maybe we can swap some things around
|
// Ok maybe we can swap some things around
|
||||||
// let vars: Vec<u64> = cur_options
|
let vars: Vec<u64> = cur_options
|
||||||
// .iter()
|
.iter()
|
||||||
// .filter(|a| a.is_var())
|
.filter(|a| a.is_var())
|
||||||
// .map(|a| {
|
.map(|a| {
|
||||||
// let (idx, _) = a.to_var();
|
let (idx, _) = a.to_var();
|
||||||
// idx
|
idx
|
||||||
// })
|
})
|
||||||
// .collect();
|
.collect();
|
||||||
|
|
||||||
// let mut possible_swap = Vec::new();
|
let mut possible_swap = Vec::new();
|
||||||
|
|
||||||
// for (k, v) in hash_t.clone() {
|
for (k, v) in hash_t.clone() {
|
||||||
// if k.is_var() {
|
if k.is_var() {
|
||||||
// let mut count_exact = 0;
|
let mut count_exact = 0;
|
||||||
// for i in v.iter() {
|
for i in v.iter() {
|
||||||
// if i.is_var() {
|
if i.is_var() {
|
||||||
// let (_id, c) = i.to_var();
|
let (_id, c) = i.to_var();
|
||||||
// if c.abs() == 1 {
|
if c.abs() == 1 {
|
||||||
// count_exact += 1;
|
count_exact += 1;
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
// println!(
|
println!(
|
||||||
// "Trying to find swap on {:?} = {:?} =====> {} {}({:?})",
|
"Trying to find swap on {:?} = {:?} =====> {} {}({:?})",
|
||||||
// k,
|
k,
|
||||||
// v,
|
v,
|
||||||
// count_exact,
|
count_exact,
|
||||||
// vars.len(),
|
vars.len(),
|
||||||
// vars
|
vars
|
||||||
// );
|
);
|
||||||
// if count_exact >= 1 {
|
if count_exact >= 1 {
|
||||||
// possible_swap.push(k.clone());
|
possible_swap.push(k.clone());
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
|
|
||||||
// if possible_swap.len() >= 1 {
|
if possible_swap.len() >= 1 {
|
||||||
// println!("We can swap! picking randomly from {:?}", possible_swap);
|
println!("We can swap! picking randomly from {:?}", possible_swap);
|
||||||
|
|
||||||
// let k = *possible_swap.choose(&mut rand::thread_rng()).unwrap();
|
let k = *possible_swap.choose(&mut rand::thread_rng()).unwrap();
|
||||||
|
|
||||||
// if !hash_t.find_1_coe_on_other_side_and_swap(k) {
|
if !hash_t.find_1_coe_on_other_side_and_swap(k) {
|
||||||
// panic!("unrechable");
|
panic!("unrechable");
|
||||||
// }
|
}
|
||||||
|
|
||||||
// sol2 += hash_t.cleanup().unwrap();
|
sol2 += hash_t.cleanup().unwrap();
|
||||||
|
|
||||||
// println!("Swapped!");
|
println!("Swapped!");
|
||||||
// // Get the one based on the index
|
// Get the one based on the index
|
||||||
// let cur_options = hash_t.remove(&EqPart::Index(i)).unwrap();
|
let cur_options = hash_t.remove(&EqPart::Index(i)).unwrap();
|
||||||
// // Insert the actual value one
|
// Insert the actual value one
|
||||||
// let k = EqPart::Num(machine.req[i] as i64);
|
let k = EqPart::Num(machine.req[i] as i64);
|
||||||
// hash_t.insert(k, cur_options.clone());
|
hash_t.insert(k, cur_options.clone());
|
||||||
|
|
||||||
// if !hash_t.find_1_coe_on_other_side_and_swap(k) {
|
if !hash_t.find_1_coe_on_other_side_and_swap(k) {
|
||||||
// println!(
|
println!(
|
||||||
// "Failed trying later {:?} try_ing one more time even with swap",
|
"Failed trying later {:?} try_ing one more time even with swap",
|
||||||
// cur_options
|
cur_options
|
||||||
// );
|
);
|
||||||
// let cur_options = hash_t.remove(&k).unwrap();
|
let cur_options = hash_t.remove(&k).unwrap();
|
||||||
// hash_t.insert(EqPart::Index(i), cur_options);
|
hash_t.insert(EqPart::Index(i), cur_options);
|
||||||
// // In this case we don't restore to the index based one
|
// In this case we don't restore to the index based one
|
||||||
// try_later_2.push(i);
|
try_later_2.push(i);
|
||||||
// continue 'try_later;
|
continue 'try_later;
|
||||||
// }
|
}
|
||||||
|
|
||||||
// continue 'try_later;
|
continue 'try_later;
|
||||||
// }
|
}
|
||||||
// println!(
|
println!(
|
||||||
// "Failed trying later {:?} try_ing one more time",
|
"Failed trying later {:?} try_ing one more time",
|
||||||
// cur_options
|
cur_options
|
||||||
// );
|
);
|
||||||
// try_later_2.push(i);
|
try_later_2.push(i);
|
||||||
// continue;
|
continue;
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
|
|
||||||
// let mut try_later_3 = Vec::new();
|
let mut try_later_3 = Vec::new();
|
||||||
// if try_later_2.len() > 0 {
|
if try_later_2.len() > 0 {
|
||||||
// println!("!!!Still some failirues last try!!!");
|
println!("!!!Still some failirues last try!!!");
|
||||||
// sol2 += hash_t.cleanup().unwrap();
|
sol2 += hash_t.cleanup().unwrap();
|
||||||
// for i in try_later_2 {
|
for i in try_later_2 {
|
||||||
// let k_org = EqPart::Index(i);
|
let k_org = EqPart::Index(i);
|
||||||
// println!("Trying to find divisors for {:?}", k_org);
|
println!("Trying to find divisors for {:?}", k_org);
|
||||||
// if !k_org.is_var() {
|
if !k_org.is_var() {
|
||||||
// let mut ops = hash_t.remove(&k_org).unwrap();
|
let mut ops = hash_t.remove(&k_org).unwrap();
|
||||||
// let org = ops.clone();
|
let org = ops.clone();
|
||||||
// let num = ops.pop_num().unwrap_or(0);
|
let num = ops.pop_num().unwrap_or(0);
|
||||||
// let k = machine.req[i] as i64 + -num;
|
let k = machine.req[i] as i64 + -num;
|
||||||
// if ops.len() == 0 && k == 0 {
|
if ops.len() == 0 && k == 0 {
|
||||||
// println!("Found inline sol for {}", i);
|
println!("Found inline sol for {}", i);
|
||||||
// continue;
|
continue;
|
||||||
// }
|
}
|
||||||
// let div = if ops.len() > 1 {
|
let div = if ops.len() > 1 {
|
||||||
// //
|
//
|
||||||
// // Check to see if everyone is div by min
|
// Check to see if everyone is div by min
|
||||||
// //
|
//
|
||||||
// let vars: Vec<Var> = ops
|
let vars: Vec<Var> = ops
|
||||||
// .clone()
|
.clone()
|
||||||
// .into_iter()
|
.into_iter()
|
||||||
// .filter(|a| a.is_var())
|
.filter(|a| a.is_var())
|
||||||
// .map(|a| a.to_var())
|
.map(|a| a.to_var())
|
||||||
// .collect();
|
.collect();
|
||||||
|
|
||||||
// let min = vars.iter().fold(i64::MAX, |m, (_, c)| m.min(c.abs()));
|
let min = vars.iter().fold(i64::MAX, |m, (_, c)| m.min(c.abs()));
|
||||||
|
|
||||||
// if !(k.abs() % min == 0
|
if !(k.abs() % min == 0
|
||||||
// && vars.iter().all(|(_, v)| v.abs() % min == 0))
|
&& vars.iter().all(|(_, v)| v.abs() % min == 0))
|
||||||
// {
|
{
|
||||||
// println!(
|
println!(
|
||||||
// "--Could not find eql divisor for {} = {:?}",
|
"--Could not find eql divisor for {} = {:?}",
|
||||||
// machine.req[i] as i64, org
|
machine.req[i] as i64, org
|
||||||
// );
|
);
|
||||||
// hash_t.insert(EqPart::Index(i), org);
|
hash_t.insert(EqPart::Index(i), org);
|
||||||
// try_later_3.push(i);
|
try_later_3.push(i);
|
||||||
// continue;
|
continue;
|
||||||
// }
|
}
|
||||||
|
|
||||||
// min
|
min
|
||||||
// } else {
|
} else {
|
||||||
// let (_id, v) = ops[0].to_var();
|
let (_id, v) = ops[0].to_var();
|
||||||
// if k.abs() % v.abs() != 0 {
|
if k.abs() % v.abs() != 0 {
|
||||||
// println!(
|
println!(
|
||||||
// "Could not find eql divisor for {} = {:?}",
|
"Could not find eql divisor for {} = {:?}",
|
||||||
// machine.req[i], org
|
machine.req[i], org
|
||||||
// );
|
);
|
||||||
// hash_t.insert(EqPart::Index(i), org);
|
hash_t.insert(EqPart::Index(i), org);
|
||||||
// try_later_3.push(i);
|
try_later_3.push(i);
|
||||||
// continue;
|
continue;
|
||||||
// }
|
}
|
||||||
// v.abs()
|
v.abs()
|
||||||
// };
|
};
|
||||||
|
|
||||||
// println!(
|
println!(
|
||||||
// "Found divisor for {:?} => {} = {:?} at {}",
|
"Found divisor for {:?} => {} = {:?} at {}",
|
||||||
// k_org, machine.req[i], org, div,
|
k_org, machine.req[i], org, div,
|
||||||
// );
|
);
|
||||||
|
|
||||||
// let k = k / div;
|
let k = k / div;
|
||||||
// let ops: Vec<EqPart> = ops
|
let ops: Vec<EqPart> = ops
|
||||||
// .into_iter()
|
.into_iter()
|
||||||
// .map(|mut m| {
|
.map(|mut m| {
|
||||||
// m.i_div(div);
|
m.i_div(div);
|
||||||
// m
|
m
|
||||||
// })
|
})
|
||||||
// .collect();
|
.collect();
|
||||||
|
|
||||||
// let k = EqPart::Num(k);
|
let k = EqPart::Num(k);
|
||||||
// hash_t.insert(k, ops);
|
hash_t.insert(k, ops);
|
||||||
// if !hash_t.find_1_coe_on_other_side_and_swap(k) {
|
if !hash_t.find_1_coe_on_other_side_and_swap(k) {
|
||||||
// panic!(
|
panic!(
|
||||||
// "this should be impossilbe we kinda of grarantee that there will always a div"
|
"this should be impossilbe we kinda of grarantee that there will always a div"
|
||||||
// );
|
);
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
|
|
||||||
// sol2 += hash_t.cleanup().unwrap();
|
sol2 += hash_t.cleanup().unwrap();
|
||||||
// }
|
}
|
||||||
// return (sol2, try_later_3);
|
return (sol2, try_later_3);
|
||||||
// }
|
}
|
||||||
|
|
||||||
// let mut loop_c = 1;
|
let mut loop_c = 1;
|
||||||
// loop {
|
loop {
|
||||||
// let (t_sol2, t2) = try_later_mult(&mut hash_t, &machine, try_later);
|
let (t_sol2, t2) = try_later_mult(&mut hash_t, &machine, try_later);
|
||||||
// sol2 += t_sol2;
|
sol2 += t_sol2;
|
||||||
// if t2.len() == 0 {
|
if t2.len() == 0 {
|
||||||
// break;
|
break;
|
||||||
// }
|
}
|
||||||
// if loop_c % 1000 == 0 {
|
if loop_c % 50 == 0 {
|
||||||
// println!("Could not simply any fruther");
|
println!("Could not simply any fruther");
|
||||||
// for i in t2 {
|
for i in t2 {
|
||||||
// let mut to_r = hash_t.remove(&EqPart::Index(i)).unwrap();
|
let mut to_r = hash_t.remove(&EqPart::Index(i)).unwrap();
|
||||||
// let num = to_r.pop_num().unwrap_or(0);
|
let num = to_r.pop_num().unwrap_or(0);
|
||||||
// hash_t.insert(EqPart::Num(machine.req[i] as i64 - num), to_r);
|
hash_t.insert(EqPart::Num(machine.req[i] as i64 - num), to_r);
|
||||||
// }
|
}
|
||||||
// sol2 += hash_t.cleanup().unwrap();
|
sol2 += hash_t.cleanup().unwrap();
|
||||||
// break;
|
break;
|
||||||
// }
|
}
|
||||||
// try_later = t2;
|
try_later = t2;
|
||||||
// loop_c += 1;
|
loop_c += 1;
|
||||||
// }
|
}
|
||||||
// }
|
|
||||||
|
|
||||||
for i in try_later {
|
|
||||||
let mut to_r = hash_t.remove(&EqPart::Index(i)).unwrap();
|
|
||||||
let num = to_r.pop_num().unwrap_or(0);
|
|
||||||
hash_t.insert(EqPart::Num(machine.req[i] as i64 - num), to_r);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
sol2 += hash_t.cleanup().unwrap();
|
sol2 += hash_t.cleanup().unwrap();
|
||||||
@@ -929,90 +889,6 @@ fn main() -> Result<()> {
|
|||||||
|
|
||||||
println!("colected vars {:?}", vars);
|
println!("colected vars {:?}", vars);
|
||||||
|
|
||||||
// loop {
|
|
||||||
// let mut cleanup: Vec<u64> = Vec::new();
|
|
||||||
// 'vars: for v in vars.iter() {
|
|
||||||
// let mut neg_one_count = 0;
|
|
||||||
// 'part: for part in hash_t.values() {
|
|
||||||
// let n = match part
|
|
||||||
// .iter()
|
|
||||||
// .find(|a| if let EqPart::Num(_) = *a { true } else { false })
|
|
||||||
// {
|
|
||||||
// Some(EqPart::Num(v)) => v,
|
|
||||||
// None => &0,
|
|
||||||
// a => panic!("not sure what to do here {:?} -> {:?}", part, a),
|
|
||||||
// };
|
|
||||||
// let mut other_vars = 0;
|
|
||||||
// let mut our_found = false;
|
|
||||||
// for item in part.iter() {
|
|
||||||
// if let EqPart::Var(idx, v_value) = item {
|
|
||||||
// if *idx != *v {
|
|
||||||
// other_vars += 1;
|
|
||||||
// } else {
|
|
||||||
// our_found = true;
|
|
||||||
// // If the value is negative one it does not change the number
|
|
||||||
// // of clicks so we can remove if all other parts are also right
|
|
||||||
// if *v_value == -1 {
|
|
||||||
// if neg_one_count == 0 {
|
|
||||||
// neg_one_count += 1;
|
|
||||||
// continue 'part;
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// // If the number is positive and our value
|
|
||||||
// // is negative we can not skip it because this means
|
|
||||||
// // that we might be able to lower the num
|
|
||||||
// if *n > 0 && *v_value < 0 {
|
|
||||||
// println!(
|
|
||||||
// "cannot clean up {} because number is positive and we are negative",
|
|
||||||
// (v + 97) as u8 as char
|
|
||||||
// );
|
|
||||||
// continue 'vars;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// // If the number is negative and our value
|
|
||||||
// // is positive we can not skip it because this means
|
|
||||||
// // that we MUST be able to raise the num
|
|
||||||
// if *n < 0 && *v_value > 0 {
|
|
||||||
// println!(
|
|
||||||
// "cannot clean up {} because number is negative and we are positive",
|
|
||||||
// (v + 97) as u8 as char
|
|
||||||
// );
|
|
||||||
// continue 'vars;
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// // If our is not found then we can just skip this part
|
|
||||||
// if !our_found {
|
|
||||||
// continue 'part;
|
|
||||||
// }
|
|
||||||
// // If one of the other checks did not catch here
|
|
||||||
// // but we have other vars we cannot really clean it up
|
|
||||||
// if other_vars > 0 {
|
|
||||||
// println!(
|
|
||||||
// "cannot clean up {} because there are other var",
|
|
||||||
// (v + 97) as u8 as char
|
|
||||||
// );
|
|
||||||
// continue 'vars;
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// // If were able pass through all the parts that
|
|
||||||
// // means we are able to clean up
|
|
||||||
// println!("Clearning up {}", (v + 97) as u8 as char);
|
|
||||||
// cleanup.push(*v);
|
|
||||||
// }
|
|
||||||
// if cleanup.len() == 0 {
|
|
||||||
// break;
|
|
||||||
// }
|
|
||||||
// for var in cleanup {
|
|
||||||
// for v in hash_t.values_mut() {
|
|
||||||
// v.smart_insert(EqPart::Var(var, 1), Vec::new());
|
|
||||||
// }
|
|
||||||
// vars.remove(&var);
|
|
||||||
// }
|
|
||||||
// sol2 += hash_t.cleanup().unwrap();
|
|
||||||
// }
|
|
||||||
|
|
||||||
if vars.len() == 0 {
|
if vars.len() == 0 {
|
||||||
println!("finsihed machine with {}", sol2);
|
println!("finsihed machine with {}", sol2);
|
||||||
sol2_main += sol2;
|
sol2_main += sol2;
|
||||||
@@ -1031,24 +907,12 @@ fn main() -> Result<()> {
|
|||||||
if var.is_none() {
|
if var.is_none() {
|
||||||
continue 'part;
|
continue 'part;
|
||||||
}
|
}
|
||||||
let (idx, var) = var.unwrap();
|
let (_, var) = var.unwrap();
|
||||||
|
|
||||||
// n is positive and we are negative then
|
|
||||||
// we can only really go up to the n
|
|
||||||
if n > 0 && var < 0 && part.len() == 2 {
|
if n > 0 && var < 0 && part.len() == 2 {
|
||||||
max = max.min(n / var.abs());
|
max = max.min(n / var.abs());
|
||||||
}
|
}
|
||||||
|
|
||||||
// n is positive and we are negative and we are the
|
|
||||||
// only things here
|
|
||||||
// then we have a min
|
|
||||||
// println!(
|
|
||||||
// "h: {} {} {} {}",
|
|
||||||
// (idx + 97) as u8 as char,
|
|
||||||
// n,
|
|
||||||
// var,
|
|
||||||
// part.len()
|
|
||||||
// );
|
|
||||||
if n < 0 && var > 0 && part.len() == 2 {
|
if n < 0 && var > 0 && part.len() == 2 {
|
||||||
min = min.max(((n.abs() as f64) / var as f64).ceil() as i64);
|
min = min.max(((n.abs() as f64) / var as f64).ceil() as i64);
|
||||||
}
|
}
|
||||||
@@ -1130,8 +994,6 @@ fn main() -> Result<()> {
|
|||||||
println!("finsihed machine with {}", sol2);
|
println!("finsihed machine with {}", sol2);
|
||||||
|
|
||||||
sol2_main += sol2;
|
sol2_main += sol2;
|
||||||
|
|
||||||
// panic!("todo");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
println!("Sol2: {}", sol2_main);
|
println!("Sol2: {}", sol2_main);
|
||||||
|
|||||||
@@ -120,6 +120,5 @@ fn sol2() -> Result<()> {
|
|||||||
|
|
||||||
fn main() -> Result<()> {
|
fn main() -> Result<()> {
|
||||||
sol1()?;
|
sol1()?;
|
||||||
sol2()?;
|
sol2()
|
||||||
Ok(())
|
|
||||||
}
|
}
|
||||||
|
|||||||
1030
src/day12/act.txt
Normal file
1030
src/day12/act.txt
Normal file
File diff suppressed because it is too large
Load Diff
448
src/day12/main.rs
Normal file
448
src/day12/main.rs
Normal file
@@ -0,0 +1,448 @@
|
|||||||
|
use anyhow::Result;
|
||||||
|
use std::{
|
||||||
|
collections::{HashMap, HashSet},
|
||||||
|
fmt::Debug,
|
||||||
|
fs,
|
||||||
|
};
|
||||||
|
|
||||||
|
#[derive(Debug)]
|
||||||
|
struct Area {
|
||||||
|
width: u64,
|
||||||
|
height: u64,
|
||||||
|
reqs: Vec<usize>,
|
||||||
|
hash: HashMap<usize, usize>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Into<Area> for &str {
|
||||||
|
fn into(self) -> Area {
|
||||||
|
let mut niter = self.split(":");
|
||||||
|
let mut positer = niter.next().unwrap().split("x");
|
||||||
|
let width: u64 = positer.next().unwrap().parse().unwrap();
|
||||||
|
let height: u64 = positer.next().unwrap().parse().unwrap();
|
||||||
|
let (reqs, hash) = niter.next().unwrap().trim().split(" ").enumerate().fold(
|
||||||
|
(Vec::new(), HashMap::new()),
|
||||||
|
|(mut v, mut h), (i, to_num)| {
|
||||||
|
h.insert(i, to_num.parse().unwrap());
|
||||||
|
for _ in 0..to_num.parse().unwrap() {
|
||||||
|
v.push(i);
|
||||||
|
}
|
||||||
|
(v, h)
|
||||||
|
},
|
||||||
|
);
|
||||||
|
Area {
|
||||||
|
width,
|
||||||
|
height,
|
||||||
|
reqs,
|
||||||
|
hash,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn try_all_vars(
|
||||||
|
area: &Area,
|
||||||
|
shapes: &HashMap<usize, Vec<StrictShape>>,
|
||||||
|
list_of_reqs: Vec<usize>,
|
||||||
|
cur_shape: StrictShape,
|
||||||
|
) -> bool {
|
||||||
|
if list_of_reqs.len() == 0 {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
let mut reqs = list_of_reqs.clone().into_iter();
|
||||||
|
let cur_idx = reqs.next().unwrap();
|
||||||
|
let reqs: Vec<usize> = reqs.collect();
|
||||||
|
|
||||||
|
// TODO check if the current shape fits in the box
|
||||||
|
|
||||||
|
// We don't have to loop because if we can not fit the first
|
||||||
|
// we will never be able to fit any way
|
||||||
|
for s in shapes.get(&cur_idx).unwrap().iter() {
|
||||||
|
let possibles = cur_shape.try_to_attach_all(area, &s);
|
||||||
|
for p in possibles {
|
||||||
|
if try_all_vars(area, shapes, reqs.clone(), p) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
false
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Area {
|
||||||
|
fn valid(&self, shapes: &HashMap<usize, Vec<StrictShape>>) -> bool {
|
||||||
|
let mut reqs = self.reqs.clone().into_iter();
|
||||||
|
let cur_idx = reqs.next().unwrap();
|
||||||
|
let reqs: Vec<usize> = reqs.collect();
|
||||||
|
|
||||||
|
// TODO check if the current shape fits in the box
|
||||||
|
|
||||||
|
// We don't have to loop because if we can not fit the first
|
||||||
|
// we will never be able to fit any way
|
||||||
|
// also we only need to test one here and this one "sets" the orientaion of the world
|
||||||
|
if try_all_vars(
|
||||||
|
self,
|
||||||
|
shapes,
|
||||||
|
reqs.clone(),
|
||||||
|
shapes.get(&cur_idx).unwrap().iter().next().unwrap().clone(),
|
||||||
|
) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Eq, PartialEq, Clone, Hash)]
|
||||||
|
struct Shape {
|
||||||
|
lines: Vec<Vec<bool>>,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Eq, PartialEq, Clone, Hash)]
|
||||||
|
// It can not rotate or flip but it's faster for comparions
|
||||||
|
struct StrictShape {
|
||||||
|
lines: Vec<u64>,
|
||||||
|
width: i64,
|
||||||
|
}
|
||||||
|
|
||||||
|
const ALL_ONES: u64 = 0b1111111111111111111111111111111111111111111111111111111111111111;
|
||||||
|
|
||||||
|
impl StrictShape {
|
||||||
|
fn get_attach_poins(&self) -> Vec<(i64, i64)> {
|
||||||
|
let mut attach_points = Vec::new();
|
||||||
|
for (y, line) in self.lines.iter().enumerate() {
|
||||||
|
let mut line = *line ^ ALL_ONES;
|
||||||
|
while line != 0 {
|
||||||
|
let i = line.trailing_zeros();
|
||||||
|
line ^= 1 << i;
|
||||||
|
if 64 - i < self.width as u32 {
|
||||||
|
attach_points.push((y as i64, 64 - i as i64));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
attach_points
|
||||||
|
}
|
||||||
|
|
||||||
|
fn get_size(&self) -> (i64, i64) {
|
||||||
|
(self.lines.len() as i64, self.width)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn try_to_attach(&self, to_attach: &StrictShape, y: i64, x: i64) -> Option<StrictShape> {
|
||||||
|
// Calculate the matrix
|
||||||
|
let (s_h, s_w) = self.get_size();
|
||||||
|
let (a_h, a_w) = to_attach.get_size();
|
||||||
|
let height = if y < 0 {
|
||||||
|
(y.abs() + s_h).max(a_h + y)
|
||||||
|
} else {
|
||||||
|
s_h.max(a_h + y)
|
||||||
|
};
|
||||||
|
let width = if x < 0 {
|
||||||
|
(x.abs() + s_w).max(a_w + x)
|
||||||
|
} else {
|
||||||
|
s_w.max(a_w + x)
|
||||||
|
};
|
||||||
|
|
||||||
|
let mut lines = Vec::new();
|
||||||
|
// i_<> is the offset into the to_attach shape it can go out of bounds on the positive side
|
||||||
|
// o_<> is the offset into the self shape it can go out of bound both sides
|
||||||
|
for i_y in 0..height {
|
||||||
|
let self_y = i_y + y.min(0);
|
||||||
|
let to_y = i_y - y.max(0);
|
||||||
|
|
||||||
|
if (self_y < 0 || self_y >= s_h) && (to_y < 0 || to_y >= a_h) {
|
||||||
|
lines.push(0);
|
||||||
|
} else if self_y < 0 || self_y >= s_h {
|
||||||
|
lines.push(to_attach.lines[to_y as usize] >> x.max(0));
|
||||||
|
} else if to_y < 0 || to_y >= a_h {
|
||||||
|
lines.push(self.lines[self_y as usize] >> x.min(0).abs());
|
||||||
|
} else {
|
||||||
|
let a_line = to_attach.lines[to_y as usize] >> x.max(0);
|
||||||
|
let self_line = self.lines[self_y as usize] >> x.min(0).abs();
|
||||||
|
// There is an itersection
|
||||||
|
if a_line & self_line > 0 {
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
lines.push(a_line | self_line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Some(StrictShape { lines, width })
|
||||||
|
}
|
||||||
|
|
||||||
|
fn try_to_attach_all(&self, area: &Area, to_attach: &StrictShape) -> Vec<StrictShape> {
|
||||||
|
// println!(
|
||||||
|
// "Trying to attach {:?} \n{:?}\n with \n{:?}\n",
|
||||||
|
// area, self, to_attach
|
||||||
|
// );
|
||||||
|
let (s_y, s_x) = self.get_size();
|
||||||
|
let (a_y, a_x) = to_attach.get_size();
|
||||||
|
|
||||||
|
let min_x = (-(a_x as i64)).max(-(area.width as i64 - s_x));
|
||||||
|
let max_x = (s_x + a_x).min(area.width as i64 - a_x as i64);
|
||||||
|
|
||||||
|
let min_y = (-(a_y as i64)).max(-(area.height as i64 - s_y));
|
||||||
|
let max_y = (s_y + a_y).min(area.height as i64 - a_y as i64);
|
||||||
|
|
||||||
|
if min_x > max_x || min_y > max_y {
|
||||||
|
//println!("Could never attach");
|
||||||
|
return Vec::new();
|
||||||
|
}
|
||||||
|
|
||||||
|
// println!("found bounds {} {} -> {} {}", min_y, min_x, max_y, max_x);
|
||||||
|
// Try edges
|
||||||
|
let mut new_possible_shapes = Vec::new();
|
||||||
|
for y in min_y..0 {
|
||||||
|
for x in min_x..=max_x {
|
||||||
|
if let Some(merged) = self.try_to_attach(to_attach, y, x) {
|
||||||
|
// println!("Found shape {y} {x} {merged:?} ");
|
||||||
|
new_possible_shapes.push(merged);
|
||||||
|
} else {
|
||||||
|
// println!("Could not find shape {y} {x}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for y in s_y..=max_y {
|
||||||
|
for x in min_x..max_x {
|
||||||
|
if let Some(merged) = self.try_to_attach(to_attach, y, x) {
|
||||||
|
// println!("Found shape {y} {x} {merged:?} ");
|
||||||
|
new_possible_shapes.push(merged);
|
||||||
|
} else {
|
||||||
|
// println!("Could not find shape {y} {x}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for y in 0..=(s_y).min(max_y) {
|
||||||
|
for x in min_x..0 {
|
||||||
|
if let Some(merged) = self.try_to_attach(to_attach, y, x) {
|
||||||
|
// println!("Found shape {y} {x} {merged:?} ");
|
||||||
|
new_possible_shapes.push(merged);
|
||||||
|
} else {
|
||||||
|
// println!("Could not find shape {y} {x}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for x in s_x..max_x {
|
||||||
|
if let Some(merged) = self.try_to_attach(to_attach, y, x) {
|
||||||
|
// println!("Found shape {y} {x} {merged:?} ");
|
||||||
|
new_possible_shapes.push(merged);
|
||||||
|
} else {
|
||||||
|
// println!("Could not find shape {y} {x}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let r_y = min_y..=max_y;
|
||||||
|
let r_x = min_x..=max_x;
|
||||||
|
|
||||||
|
for (p_y, p_x) in self.get_attach_poins() {
|
||||||
|
// println!("in {p_y} {p_x}");
|
||||||
|
if r_y.contains(&p_y) && r_x.contains(&p_x) {
|
||||||
|
if let Some(merged) = self.try_to_attach(to_attach, p_y, p_x) {
|
||||||
|
// println!("Found shape {p_y} {p_x}{merged:?}");
|
||||||
|
new_possible_shapes.push(merged);
|
||||||
|
} else {
|
||||||
|
// println!("Could not find shape {p_y} {p_x}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
new_possible_shapes.sort_by(|a, b| {
|
||||||
|
(a.width * a.lines.len() as i64).cmp(&(b.width * b.lines.len() as i64))
|
||||||
|
});
|
||||||
|
|
||||||
|
// if new_possible_shapes > 0 {
|
||||||
|
// println!("Best shape {:?}", new_possible_shapes[0]);
|
||||||
|
// }
|
||||||
|
|
||||||
|
new_possible_shapes
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Debug for StrictShape {
|
||||||
|
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||||
|
write!(f, "\n")?;
|
||||||
|
for line in self.lines.iter() {
|
||||||
|
let line = format!("{line:064b}");
|
||||||
|
let line = line[0..(self.width as usize)]
|
||||||
|
.to_string()
|
||||||
|
.replace("0", ".")
|
||||||
|
.replace("1", "#");
|
||||||
|
write!(f, "{}\n", line)?;
|
||||||
|
}
|
||||||
|
write!(f, "")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Shape {
|
||||||
|
fn new() -> Shape {
|
||||||
|
Shape { lines: Vec::new() }
|
||||||
|
}
|
||||||
|
|
||||||
|
fn add_line(&mut self, text: &str) {
|
||||||
|
let mut line = Vec::new();
|
||||||
|
for c in text.chars() {
|
||||||
|
match c {
|
||||||
|
'#' => line.push(true),
|
||||||
|
'.' => line.push(false),
|
||||||
|
c => panic!("Not sure what to do {}", c),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
self.lines.push(line);
|
||||||
|
}
|
||||||
|
|
||||||
|
fn rotate_right(&self) -> Self {
|
||||||
|
let mut lines = Vec::new();
|
||||||
|
let height = self.lines.len();
|
||||||
|
assert!(height > 0, "Something is wrong {:?}", self);
|
||||||
|
let width = self.lines[0].len();
|
||||||
|
for x in (0..width).rev() {
|
||||||
|
let mut new_line = Vec::new();
|
||||||
|
for y in 0..height {
|
||||||
|
new_line.push(self.lines[y][x]);
|
||||||
|
}
|
||||||
|
lines.push(new_line);
|
||||||
|
}
|
||||||
|
Self { lines }
|
||||||
|
}
|
||||||
|
|
||||||
|
fn flip(&self) -> Self {
|
||||||
|
let mut lines = Vec::new();
|
||||||
|
let height = self.lines.len();
|
||||||
|
let width = self.lines[0].len();
|
||||||
|
for y in (0..height).rev() {
|
||||||
|
let mut new_line = Vec::new();
|
||||||
|
for x in (0..width).rev() {
|
||||||
|
new_line.push(self.lines[y][x]);
|
||||||
|
}
|
||||||
|
lines.push(new_line);
|
||||||
|
}
|
||||||
|
Self { lines }
|
||||||
|
}
|
||||||
|
|
||||||
|
fn to_strict(self) -> StrictShape {
|
||||||
|
let mut lines = Vec::new();
|
||||||
|
for line in self.lines.iter() {
|
||||||
|
let mut n_line = 0;
|
||||||
|
for (i, c) in line.iter().enumerate() {
|
||||||
|
n_line = n_line | (*c as u64) << 63 - i;
|
||||||
|
}
|
||||||
|
lines.push(n_line);
|
||||||
|
}
|
||||||
|
|
||||||
|
StrictShape {
|
||||||
|
lines,
|
||||||
|
width: self.lines[0].len() as i64,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn get_varients(self) -> Vec<StrictShape> {
|
||||||
|
let mut shapes_list = HashSet::new();
|
||||||
|
let shape1 = self.rotate_right();
|
||||||
|
let shape2 = shape1.rotate_right();
|
||||||
|
let shape3 = shape2.rotate_right();
|
||||||
|
shapes_list.insert(shape1.to_strict());
|
||||||
|
shapes_list.insert(shape2.to_strict());
|
||||||
|
shapes_list.insert(shape3.to_strict());
|
||||||
|
let fliped = self.flip();
|
||||||
|
let shape1 = fliped.rotate_right();
|
||||||
|
let shape2 = shape1.rotate_right();
|
||||||
|
let shape3 = shape2.rotate_right();
|
||||||
|
shapes_list.insert(self.to_strict());
|
||||||
|
shapes_list.insert(fliped.to_strict());
|
||||||
|
shapes_list.insert(shape1.to_strict());
|
||||||
|
shapes_list.insert(shape2.to_strict());
|
||||||
|
shapes_list.insert(shape3.to_strict());
|
||||||
|
shapes_list.into_iter().collect()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Debug for Shape {
|
||||||
|
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||||
|
write!(f, "\n")?;
|
||||||
|
for line in self.lines.iter() {
|
||||||
|
for c in line {
|
||||||
|
write!(f, "{}", if *c { "#" } else { "." })?;
|
||||||
|
}
|
||||||
|
write!(f, "\n")?;
|
||||||
|
}
|
||||||
|
write!(f, "")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() -> Result<()> {
|
||||||
|
let text = fs::read_to_string("src/day12/act.txt")?;
|
||||||
|
|
||||||
|
let mut areas: Vec<Area> = Vec::new();
|
||||||
|
let mut shapes = HashMap::new();
|
||||||
|
let mut cur_shape = Shape::new();
|
||||||
|
|
||||||
|
for line in text.split("\n") {
|
||||||
|
if line == "" {
|
||||||
|
continue;
|
||||||
|
} else if line.contains("x") {
|
||||||
|
if cur_shape.lines.len() != 0 {
|
||||||
|
let vars = cur_shape.get_varients();
|
||||||
|
println!("Shape: {:?} {}", vars[0], vars.len());
|
||||||
|
shapes.insert(shapes.values().len(), vars);
|
||||||
|
cur_shape = Shape::new();
|
||||||
|
}
|
||||||
|
areas.push(line.into());
|
||||||
|
} else if line.contains(":") {
|
||||||
|
if cur_shape.lines.len() == 0 {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
let vars = cur_shape.get_varients();
|
||||||
|
println!("Shape: {:?} {}", vars[0], vars.len());
|
||||||
|
shapes.insert(shapes.values().len(), vars);
|
||||||
|
cur_shape = Shape::new();
|
||||||
|
} else {
|
||||||
|
cur_shape.add_line(line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let mut valid = 0;
|
||||||
|
for a in areas.iter() {
|
||||||
|
let mut count_of_1 = *a.hash.get(&1).unwrap();
|
||||||
|
let by_6 = count_of_1 / 6;
|
||||||
|
let left_over = count_of_1 % 6;
|
||||||
|
|
||||||
|
let mut area = a.width / 3 * a.height / 3;
|
||||||
|
if (a.width / 12 * a.height / 3) as usize > by_6
|
||||||
|
|| (a.width / 3 * a.height / 12) as usize > by_6
|
||||||
|
{
|
||||||
|
count_of_1 = left_over;
|
||||||
|
area -= (by_6 * 4) as u64;
|
||||||
|
}
|
||||||
|
|
||||||
|
let mut sum: u64 = 0;
|
||||||
|
for (i, v) in a.hash.iter() {
|
||||||
|
if *i == 1 {
|
||||||
|
sum += count_of_1 as u64;
|
||||||
|
} else {
|
||||||
|
sum += *v as u64;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if area >= sum {
|
||||||
|
valid += 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
println!("sol1: {}", valid);
|
||||||
|
|
||||||
|
panic!("mad");
|
||||||
|
|
||||||
|
// We know that 3 only nicly packs with itself
|
||||||
|
|
||||||
|
let mut valid = 0;
|
||||||
|
for (i, a) in areas.iter().enumerate() {
|
||||||
|
if a.valid(&shapes) {
|
||||||
|
println!("Found Valid ans {i}\n\n\n\n\n\n");
|
||||||
|
valid += 1;
|
||||||
|
} else {
|
||||||
|
println!("Could not Find valid answer {i}\n\n\n\n\n\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
println!("sol1: {}", valid);
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
33
src/day12/test.txt
Normal file
33
src/day12/test.txt
Normal file
@@ -0,0 +1,33 @@
|
|||||||
|
0:
|
||||||
|
###
|
||||||
|
##.
|
||||||
|
##.
|
||||||
|
|
||||||
|
1:
|
||||||
|
###
|
||||||
|
##.
|
||||||
|
.##
|
||||||
|
|
||||||
|
2:
|
||||||
|
.##
|
||||||
|
###
|
||||||
|
##.
|
||||||
|
|
||||||
|
3:
|
||||||
|
##.
|
||||||
|
###
|
||||||
|
##.
|
||||||
|
|
||||||
|
4:
|
||||||
|
###
|
||||||
|
#..
|
||||||
|
###
|
||||||
|
|
||||||
|
5:
|
||||||
|
###
|
||||||
|
.#.
|
||||||
|
###
|
||||||
|
|
||||||
|
4x4: 0 0 0 0 2 0
|
||||||
|
12x5: 1 0 1 0 2 2
|
||||||
|
12x5: 1 0 1 0 3 2
|
||||||
Reference in New Issue
Block a user