diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..2383c7d --- /dev/null +++ b/.gitignore @@ -0,0 +1,4 @@ +bin/ +zig-out/ +zig-cache/ +target/ diff --git a/day1/Makefile b/day1/Makefile new file mode 100644 index 0000000..9887c5c --- /dev/null +++ b/day1/Makefile @@ -0,0 +1,13 @@ +.PHONY: bench-build bench-rebuild bench + +bench-build: + hyperfine -p 'rm -f bin/main' -c 'rm -f bin/main' 'rustc --out-dir bin/ main.rs' + hyperfine -p 'rm -rf zig-out/ zig-cache/' -c 'rm -rf zig-out/ zig-cache/' '~/src/misc/zig/build/zig build' + +bench-rebuild: + hyperfine 'rustc --out-dir bin/ main.rs' + hyperfine '~/src/misc/zig/build/zig build' + +bench: + hyperfine -p 'rustc --out-dir bin/ main.rs' ./bin/main + hyperfine -p '~/src/misc/zig/build/zig build' ./zig-out/bin/day1 diff --git a/day1/build.zig b/day1/build.zig new file mode 100644 index 0000000..83ae7dc --- /dev/null +++ b/day1/build.zig @@ -0,0 +1,27 @@ +const std = @import("std"); + +pub fn build(b: *std.build.Builder) void { + // Standard target options allows the person running `zig build` to choose + // what target to build for. Here we do not override the defaults, which + // means any target is allowed, and the default is native. Other options + // for restricting supported target set are available. + const target = b.standardTargetOptions(.{}); + + // Standard release options allow the person running `zig build` to select + // between Debug, ReleaseSafe, ReleaseFast, and ReleaseSmall. + const mode = b.standardReleaseOptions(); + + const exe = b.addExecutable("day1", "src/main.zig"); + exe.setTarget(target); + exe.setBuildMode(mode); + exe.install(); + + const run_cmd = exe.run(); + run_cmd.step.dependOn(b.getInstallStep()); + if (b.args) |args| { + run_cmd.addArgs(args); + } + + const run_step = b.step("run", "Run the app"); + run_step.dependOn(&run_cmd.step); +} diff --git a/day1/input b/day1/input new file mode 100644 index 0000000..e4f99d2 --- /dev/null +++ b/day1/input @@ -0,0 +1,100 @@ +85644 +52584 +72349 +83834 +56593 +108492 +94585 +97733 +62732 +103113 +133259 +132647 +52460 +51299 +115749 +121047 +69451 +54737 +62738 +116686 +57293 +97273 +128287 +139440 +97583 +130263 +79307 +118198 +82514 +70679 +64485 +119346 +136281 +114724 +73580 +76314 +126198 +97635 +114655 +104195 +99469 +70251 +82815 +79531 +58135 +80625 +73106 +139806 +138478 +136605 +111472 +149915 +95928 +126905 +70496 +147999 +148501 +114025 +75716 +113473 +95390 +104466 +138715 +53053 +79502 +98601 +115139 +122315 +88402 +124332 +140107 +50912 +104885 +142005 +145938 +118556 +101858 +51142 +94100 +99421 +84544 +137234 +126374 +107333 +82439 +125373 +51212 +99358 +82821 +89913 +67513 +136907 +133707 +139988 +96914 +130672 +66474 +120729 +50131 +67475 diff --git a/day1/main.rs b/day1/main.rs new file mode 100644 index 0000000..41a74ba --- /dev/null +++ b/day1/main.rs @@ -0,0 +1,29 @@ +fn main() { + let contents = std::fs::read_to_string("input") + .expect("Failed to read file 'input'"); + let it = contents.split("\n"); + let mut sum: u64 = 0; + let mut sum2: u64 = 0; + for val in it { + if val == "" { + continue; + } + let mut x = val.parse::().unwrap(); + x /= 3; + x -= 2; + sum += x; + sum2 += x; + while x > 0 { + x /= 3; + if x < 2 { + x = 0; + } + else { + x -= 2; + } + sum2 += x; + } + } + println!("[Part 1] The sum is {}", sum); + println!("[Part 2] The sum is {}", sum2); +} diff --git a/day1/src/main.zig b/day1/src/main.zig new file mode 100644 index 0000000..76abd72 --- /dev/null +++ b/day1/src/main.zig @@ -0,0 +1,36 @@ +const std = @import("std"); + +pub fn main() anyerror!void { + var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator); + defer arena.deinit(); + const alloc = &arena.allocator; + + // Read our input + var f = try std.fs.cwd().openFile("input", .{}); + defer f.close(); + var contents = try f.readToEndAlloc(alloc, std.math.maxInt(u32)); + defer alloc.free(contents); + + var it = std.mem.tokenize(contents, "\n"); + var sum: u64 = 0; + var sum2: u64 = 0; + while (it.next()) |v| { + var val: u64 = try std.fmt.parseInt(u64, v, 10); + val /= 3; + val -= 2; + sum += val; + sum2 += val; + while (val > 0) { + val /= 3; + if (val < 2) { + val = 0; + } + else { + val -= 2; + } + sum2 += val; + } + } + std.log.info("[Part 1] Sum: {}", .{sum}); + std.log.info("[Part 2] Sum: {}", .{sum2}); +} diff --git a/day2/Cargo.lock b/day2/Cargo.lock new file mode 100644 index 0000000..63c2f60 --- /dev/null +++ b/day2/Cargo.lock @@ -0,0 +1,7 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "day2" +version = "0.1.0" diff --git a/day2/Cargo.toml b/day2/Cargo.toml new file mode 100644 index 0000000..8aa34bb --- /dev/null +++ b/day2/Cargo.toml @@ -0,0 +1,8 @@ +[package] +name = "day2" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] diff --git a/day2/input b/day2/input new file mode 100644 index 0000000..dc14d67 --- /dev/null +++ b/day2/input @@ -0,0 +1 @@ +1,0,0,3,1,1,2,3,1,3,4,3,1,5,0,3,2,1,10,19,1,9,19,23,1,13,23,27,1,5,27,31,2,31,6,35,1,35,5,39,1,9,39,43,1,43,5,47,1,47,5,51,2,10,51,55,1,5,55,59,1,59,5,63,2,63,9,67,1,67,5,71,2,9,71,75,1,75,5,79,1,10,79,83,1,83,10,87,1,10,87,91,1,6,91,95,2,95,6,99,2,99,9,103,1,103,6,107,1,13,107,111,1,13,111,115,2,115,9,119,1,119,6,123,2,9,123,127,1,127,5,131,1,131,5,135,1,135,5,139,2,10,139,143,2,143,10,147,1,147,5,151,1,151,2,155,1,155,13,0,99,2,14,0,0 diff --git a/day2/src/main.rs b/day2/src/main.rs new file mode 100644 index 0000000..c9483f5 --- /dev/null +++ b/day2/src/main.rs @@ -0,0 +1,105 @@ +fn main() { + let contents = std::fs::read_to_string("input") + .expect("Failed to read file 'input'"); + let it = contents.split(","); + let mut program = Vec::new(); + for val in it { + if val.ends_with('\n') { + let mut s = String::from(val); + s.pop(); + program.push(s.parse::().unwrap()); + } + else { + program.push(val.parse::().unwrap()); + } + } + + // Create a copy of the memory to refresh from + let backup = program.clone(); + + // Modify state for part 1 + program[1] = 12; + program[2] = 2; + simulate(&mut program); + println!("[Part 1] The value at position 0 is: {}", program[0]); + + let mut noun = 0; + while noun < 100 { + let mut verb = 0; + while verb < 100 { + program = backup.clone(); + program[1] = noun; + program[2] = verb; + simulate(&mut program); + //println!("Noun {}, verb {}: {}", noun, verb, program[0]); + if program[0] == 19690720 { + println!("[Part 2] noun {}, verb {}, sum {}", noun, verb, 100*noun+verb); + break; + } + verb += 1; + } + noun += 1; + } +} + +fn simulate(v: &mut Vec) { + let mut pos = 0; + loop { + let code = v[pos]; + if code == 1 { + let i1 = v[pos+1] as usize; + let i2 = v[pos+2] as usize; + let idest = v[pos+3] as usize; + v[idest] = v[i1] + v[i2]; + pos += 4; + continue; + } + else if code == 2 { + let i1 = v[pos+1] as usize; + let i2 = v[pos+2] as usize; + let idest = v[pos+3] as usize; + v[idest] = v[i1] * v[i2]; + pos += 4; + continue; + } + else if code == 99 { + break; + } + else { + panic!("Unknown opcode"); + } + } +} + +#[cfg(test)] +mod tests { + use super::*; + #[test] + fn test_op_1() { + let mut program = vec![1, 0, 0, 0, 99]; + simulate(&mut program); + assert_eq!(program[0], 2); + } + + #[test] + fn test_op_2() { + let mut program = vec![2, 3, 0, 3, 99]; + simulate(&mut program); + assert_eq!(program[3], 6); + } + + #[test] + fn test_case_3() { + let mut program = vec![2,4,4,5,99,0]; + simulate(&mut program); + assert_eq!(program[program.len() - 1], 9801); + } + + #[test] + fn test_case_4() { + let mut program = vec![1,1,1,4,99,5,6,0,99]; + simulate(&mut program); + assert_eq!(program[0], 30); + assert_eq!(program[4], 2); + } +} diff --git a/day3/Cargo.lock b/day3/Cargo.lock new file mode 100644 index 0000000..4104d70 --- /dev/null +++ b/day3/Cargo.lock @@ -0,0 +1,7 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "day3" +version = "0.1.0" diff --git a/day3/Cargo.toml b/day3/Cargo.toml new file mode 100644 index 0000000..898e70d --- /dev/null +++ b/day3/Cargo.toml @@ -0,0 +1,8 @@ +[package] +name = "day3" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] diff --git a/day3/input b/day3/input new file mode 100644 index 0000000..ae753a6 --- /dev/null +++ b/day3/input @@ -0,0 +1,2 @@ +R990,U944,L921,U993,L64,U29,R899,D406,R841,U716,L32,U658,L830,D481,L441,U491,L687,D847,L459,U920,R165,U224,L896,D868,L191,U877,L909,U467,R798,U132,R234,U49,R484,U911,R108,D308,R867,U350,L404,U107,L84,U668,R850,U470,L182,U93,R284,U999,L664,U110,R650,D189,R540,D112,R794,U999,R871,D829,L549,U988,R654,D411,R323,D774,R529,U275,L909,U936,R122,D922,L331,U813,L748,U770,R511,D892,L770,U318,R661,U823,R210,D393,L694,U929,L76,D619,R395,U651,R526,U145,R851,U112,R73,D89,R17,U929,R807,U87,R764,D158,L820,U803,L785,D205,L828,D271,L839,D482,L797,U338,R322,D633,L292,U16,R627,U19,R548,U516,L384,U83,R256,U937,R404,U322,R671,D543,L412,U446,R238,U246,L794,D750,L34,U317,L994,U874,L247,D20,R491,U834,L498,D987,R2,U175,R452,U168,R495,D183,R201,U532,L192,U984,L566,D471,L704,D2,L776,U5,R911,U308,R763,D555,R458,D439,L968,D78,R549,D583,R289,D355,L503,D871,L881,U516,L507,D551,R711,U702,L308,D905,L408,U932,L884,U218,L158,D562,L200,D114,R673,U448,R887,U181,R247,U329,L965,U495,L329,D162,L265,D389,R419,U435,R258,U146,R208,D184,R730,D19,L78,D886,R472,D350,R484,U392,L542,U601,L202,U974,L310,U52,L537,U597,L163,D655,R928,U269,L926,D790,L513,U441,L90,U581,L211,U871,R603,D130,L220,U459,L933,U648,R721,U642,R301,U537,L858,D777,R823,U14,R820,D218,L96,D318,L206,U280,R887,D241,L752,U828,R354,U864,R844,D872,L728,D298,L234,U695,R434,D94,R905,D592,L32,D860,R680,D197,R886,U760,L232,U916,L452,U248,R715,D773,R867,U77,R751,D36,R565,U897,R782,U931,R546,U261,R920,D296,R451,U258,L394,U965,R912,D593,L990 +L994,U515,R163,U863,L343,U162,L875,D92,L483,D601,R79,D761,L389,U167,L145,U145,L247,U886,R61,U820,L584,D239,R402,U805,R956,U126,R615,D322,R431,D460,R397,D511,R805,D177,L778,U296,R599,U759,R40,U1,L422,U751,R94,U401,R504,U940,L564,U24,R595,U944,R815,U672,R787,D854,R579,D604,L62,U670,L516,U199,L639,D919,L485,U655,R391,U669,R772,D34,R868,D12,L108,U295,R701,D603,R493,U927,R29,D34,R499,U111,L87,U190,R884,D658,R474,D166,R921,U698,R592,U25,R710,D398,L26,U696,L432,D887,R469,U656,L428,D188,L543,D150,R160,U543,R743,U692,R618,D148,R956,U753,L175,D789,R897,U305,L137,D914,R330,D780,R744,D473,L754,U482,L975,D413,L698,U656,L177,U419,R13,D827,L67,D800,R369,U97,L34,D588,L41,D760,L164,U224,L921,D311,R489,U956,R277,U180,R724,U748,R785,U826,L426,D957,R303,U16,L729,U224,L712,U43,L280,D648,R987,D941,R154,D581,R876,U615,L480,D103,R636,D276,R948,U89,R434,D212,R837,D295,R532,D390,R374,D926,R911,D110,R258,U83,L955,U747,L925,D366,R571,U241,R628,D344,R919,U117,R337,D683,L720,U261,L124,D545,R979,D601,L906,D324,R441,U678,L978,U744,L472,D217,R799,U740,L77,U964,L278,U497,R441,U21,L37,U319,L24,D211,L44,U459,R35,D609,R900,D538,R397,D776,R629,D860,R519,D340,R168,U603,R46,U889,R897,D442,R997,U705,L82,D963,R941,U701,L347,D824,R269,U891,L569,D558,L867,U145,R121,D369,R542,U227,L198,U863,L755,U273,L734,D233,R578,U67,L821,U600,L203,D234,R695,U819,L639,D700,R295,D129,L612,U157,R212,U536,L968,U562,L999,D391,L231,U262,R334,D967,R463,U748,R842,D500,R860,U856,R263,D633,R460,D337,L880,U146,R910 diff --git a/day3/src/main.rs b/day3/src/main.rs new file mode 100644 index 0000000..5d07d56 --- /dev/null +++ b/day3/src/main.rs @@ -0,0 +1,178 @@ +use std::collections::HashSet; +use std::collections::HashMap; + +fn main() { + let mut contents = std::fs::read_to_string("input") + .expect("Failed to read file 'input'"); + let mut it = contents.split("\n"); + let mut line_a: HashSet = HashSet::new(); + let mut line_b: HashSet = HashSet::new(); + match it.next() { + Some(v) => get_line_points_from_str(&mut line_a, &v), + None => panic!(), + } + match it.next() { + Some(v) => { + let s = String::from(v); + get_line_points_from_str(&mut line_b, &s); + }, + None => panic!(), + } + + // Some possible approaches + // my first thought was to do the following + // 1) collect all points for line_a and line_b + // 2) create a pool of intersecting points + // 3) for all the intersecting points, which is + // closest to the origin in manhattan distance + // + // this is pretty easy, but seems like it would be + // memory hungry and doesn't scale to large lines + // bonus: rust HashSets (wrappers around HashMap) + // a union method to facilitate this task. + // + // another thought I had was to find and use some + // sort of math things to compare to pair of line + // segments to see if they intersect, and if so - where. + + let mut closest_point: Point = Point {x: 0, y: 0}; + let mut closest_distance = i32::MAX; + let mut intersects: HashSet = HashSet::new(); + for p in line_a.intersection(&line_b) { + if p.x == 0 && p.y == 0 { + continue; + } + intersects.insert(Point {x: p.x, y: p.y}); + let distance = p.x.abs() + p.y.abs(); + //println!("Intersection: {},{} distance {}", + // p.x, p.y, distance); + if distance < closest_distance { + closest_point = Point {x: p.x, y: p.y}; + closest_distance = distance; + } + } + println!("[Part 1] Closest intersection {} away at {},{}", + closest_distance, closest_point.x, closest_point.y); + + // We replay the get_line_poionts_from_str, but instead + // when we reach one of the intersections we can add + // Point, steps into a result set. + let mut line_a_steps_to_intersect: HashMap = HashMap::new(); + let mut line_b_steps_to_intersect: HashMap = HashMap::new(); + contents = std::fs::read_to_string("input") + .expect("Failed to read file 'input'"); + it = contents.split("\n"); + match it.next() { + Some(v) => get_steps_to_intersections(&intersects, v, + &mut line_a_steps_to_intersect), + None => panic!(), + } + match it.next() { + Some(v) => get_steps_to_intersections(&intersects, v, + &mut line_b_steps_to_intersect), + None => panic!(), + } + let mut step_sum = u64::MAX; + let iit = intersects.iter(); + for p in iit { + let new_sum = line_a_steps_to_intersect.get(&p).unwrap() + + line_b_steps_to_intersect.get(&p).unwrap(); + if new_sum < step_sum { + step_sum = new_sum; + closest_point = Point {x: p.x, y: p.y}; + } + } + println!("[Part 2] Intersection {},{} is {} steps away", + closest_point.x, closest_point.y, step_sum); +} + +fn get_steps_to_intersections(points: &HashSet, source: &str, map: &mut HashMap) { + let mut x = 0; + let mut y = 0; + let mut total_steps = 0; + let lit = source.split(","); + for val in lit { + let dir = val.chars().nth(0).unwrap(); + let mut dx = 0; + let mut dy = 0; + let v = val[1..].parse::().unwrap(); + match dir { + 'U' => dy = 1, + 'D' => dy = -1, + 'L' => dx = -1, + 'R' => dx = 1, + _ => panic!(), + } + let mut needed_steps = 0; + if dx != 0 { + needed_steps = v; + needed_steps = needed_steps.abs(); + } + if dy != 0 { + needed_steps = v; + needed_steps = needed_steps.abs(); + } + let mut step = 0; + while step < needed_steps { + x += dx; + y += dy; + total_steps += 1; + let p = Point {x: x, y: y}; + if points.contains(&p) { + //println!("Inserting intersection {},{} at {} steps", + //p.x, p.y, total_steps); + map.insert(p, total_steps); + } + step += 1; + } + } +} + +fn get_line_points_from_str(points: &mut HashSet, source: &str) { + let mut x = 0; + let mut y = 0; + points.insert(Point { x: x, y: y }); + let lit = source.split(","); + for val in lit { + let dir = val.chars().nth(0).unwrap(); + let mut dx = 0; + let mut dy = 0; + let v = val[1..].parse::().unwrap(); + match dir { + 'U' => dy = 1, + 'D' => dy = -1, + 'L' => dx = -1, + 'R' => dx = 1, + _ => panic!(), + } + let mut needed_steps = 0; + if dx != 0 { + needed_steps = v; + needed_steps = needed_steps.abs(); + } + if dy != 0 { + needed_steps = v; + needed_steps = needed_steps.abs(); + } + //println!("Walking from {},{} {}{} (step {},{} {} times)", + //x, y, dir, v, dx, dy, needed_steps); + let mut step = 0; + while step < needed_steps { + x += dx; + y += dy; + //println!("Adding {},{}", x, y); + points.insert(Point {x: x, y: y}); + step += 1; + } + } +} + +#[derive(PartialEq, Eq, Hash)] +struct Point { + x: i32, + y: i32, +} +#[cfg(test)] +mod tests { + +} diff --git a/day3/testinput b/day3/testinput new file mode 100644 index 0000000..73b95a1 --- /dev/null +++ b/day3/testinput @@ -0,0 +1,2 @@ +R8,U5,L5,D3 +U7,R6,D4,L4 diff --git a/day4/Cargo.lock b/day4/Cargo.lock new file mode 100644 index 0000000..e92c02c --- /dev/null +++ b/day4/Cargo.lock @@ -0,0 +1,7 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "day4" +version = "0.1.0" diff --git a/day4/Cargo.toml b/day4/Cargo.toml new file mode 100644 index 0000000..8842130 --- /dev/null +++ b/day4/Cargo.toml @@ -0,0 +1,8 @@ +[package] +name = "day4" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] diff --git a/day4/src/main.rs b/day4/src/main.rs new file mode 100644 index 0000000..b05e60e --- /dev/null +++ b/day4/src/main.rs @@ -0,0 +1,101 @@ +fn main() { + let min = [1, 9, 3, 6, 5, 1]; + let max = [6, 4, 9, 7, 2, 9]; + + let mut matches = 0; + let mut i = min.clone(); + loop { + // Check for a adjacents + if i[0] == i[1] || + i[1] == i[2] || + i[2] == i[3] || + i[3] == i[4] || + i[4] == i[5] + { + // Check for incrementing + if i[0] <= i[1] && + i[1] <= i[2] && + i[2] <= i[3] && + i[3] <= i[4] && + i[4] <= i[5] + { + //println!("{:?} matches", i); + matches += 1; + } + } + let mut x = 5; + loop { + i[x] += 1; + if i[x] >= 10 { + i[x] -= 10; + x -= 1; + continue + } + break; + } + if i[0] >= max[0] && + i[1] >= max[1] && + i[2] >= max[2] && + i[3] >= max[3] && + i[4] >= max[4] && + i[5] >= max[5] { + break; + } + } + println!("[Part 1] There are {} potential matches", matches); + + i = min.clone(); + matches = 0; + loop { + // Check for incrementing + if i[0] <= i[1] && + i[1] <= i[2] && + i[2] <= i[3] && + i[3] <= i[4] && + i[4] <= i[5] + { + // Check for groups + let mut idx = 0; + let mut has_two_chain = false; + let mut chain_size = 1; + while idx < 5 { + if i[idx] == i[idx+1] { + chain_size += 1; + idx += 1; + } + else { + if chain_size == 2 { + has_two_chain = true; + } + chain_size = 1; + idx += 1; + } + } + if chain_size == 2 { + has_two_chain = true; + } + if has_two_chain { + matches += 1; + } + } + let mut x = 5; + loop { + i[x] += 1; + if i[x] >= 10 { + i[x] -= 10; + x -= 1; + continue + } + break; + } + if i[0] >= max[0] && + i[1] >= max[1] && + i[2] >= max[2] && + i[3] >= max[3] && + i[4] >= max[4] && + i[5] >= max[5] { + break; + } + } + println!("[Part 2] There are {} potential matches", matches); +} diff --git a/day5/Cargo.lock b/day5/Cargo.lock new file mode 100644 index 0000000..72ffd9e --- /dev/null +++ b/day5/Cargo.lock @@ -0,0 +1,14 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "day5" +version = "0.2.0" +dependencies = [ + "icc", +] + +[[package]] +name = "icc" +version = "0.1.0" diff --git a/day5/Cargo.toml b/day5/Cargo.toml new file mode 100644 index 0000000..d09179e --- /dev/null +++ b/day5/Cargo.toml @@ -0,0 +1,9 @@ +[package] +name = "day5" +version = "0.2.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +icc = { path = "../icc", version = "0.1.0"} \ No newline at end of file diff --git a/day5/input b/day5/input new file mode 100644 index 0000000..15411a8 --- /dev/null +++ b/day5/input @@ -0,0 +1 @@ +3,225,1,225,6,6,1100,1,238,225,104,0,1102,72,20,224,1001,224,-1440,224,4,224,102,8,223,223,1001,224,5,224,1,224,223,223,1002,147,33,224,101,-3036,224,224,4,224,102,8,223,223,1001,224,5,224,1,224,223,223,1102,32,90,225,101,65,87,224,101,-85,224,224,4,224,1002,223,8,223,101,4,224,224,1,223,224,223,1102,33,92,225,1102,20,52,225,1101,76,89,225,1,117,122,224,101,-78,224,224,4,224,102,8,223,223,101,1,224,224,1,223,224,223,1102,54,22,225,1102,5,24,225,102,50,84,224,101,-4600,224,224,4,224,1002,223,8,223,101,3,224,224,1,223,224,223,1102,92,64,225,1101,42,83,224,101,-125,224,224,4,224,102,8,223,223,101,5,224,224,1,224,223,223,2,58,195,224,1001,224,-6840,224,4,224,102,8,223,223,101,1,224,224,1,223,224,223,1101,76,48,225,1001,92,65,224,1001,224,-154,224,4,224,1002,223,8,223,101,5,224,224,1,223,224,223,4,223,99,0,0,0,677,0,0,0,0,0,0,0,0,0,0,0,1105,0,99999,1105,227,247,1105,1,99999,1005,227,99999,1005,0,256,1105,1,99999,1106,227,99999,1106,0,265,1105,1,99999,1006,0,99999,1006,227,274,1105,1,99999,1105,1,280,1105,1,99999,1,225,225,225,1101,294,0,0,105,1,0,1105,1,99999,1106,0,300,1105,1,99999,1,225,225,225,1101,314,0,0,106,0,0,1105,1,99999,1107,677,226,224,1002,223,2,223,1005,224,329,101,1,223,223,7,677,226,224,102,2,223,223,1005,224,344,1001,223,1,223,1107,226,226,224,1002,223,2,223,1006,224,359,1001,223,1,223,8,226,226,224,1002,223,2,223,1006,224,374,101,1,223,223,108,226,226,224,102,2,223,223,1005,224,389,1001,223,1,223,1008,226,226,224,1002,223,2,223,1005,224,404,101,1,223,223,1107,226,677,224,1002,223,2,223,1006,224,419,101,1,223,223,1008,226,677,224,1002,223,2,223,1006,224,434,101,1,223,223,108,677,677,224,1002,223,2,223,1006,224,449,101,1,223,223,1108,677,226,224,102,2,223,223,1006,224,464,1001,223,1,223,107,677,677,224,102,2,223,223,1005,224,479,101,1,223,223,7,226,677,224,1002,223,2,223,1006,224,494,1001,223,1,223,7,677,677,224,102,2,223,223,1006,224,509,101,1,223,223,107,226,677,224,1002,223,2,223,1006,224,524,1001,223,1,223,1007,226,226,224,102,2,223,223,1006,224,539,1001,223,1,223,108,677,226,224,102,2,223,223,1005,224,554,101,1,223,223,1007,677,677,224,102,2,223,223,1006,224,569,101,1,223,223,8,677,226,224,102,2,223,223,1006,224,584,1001,223,1,223,1008,677,677,224,1002,223,2,223,1006,224,599,1001,223,1,223,1007,677,226,224,1002,223,2,223,1005,224,614,101,1,223,223,1108,226,677,224,1002,223,2,223,1005,224,629,101,1,223,223,1108,677,677,224,1002,223,2,223,1005,224,644,1001,223,1,223,8,226,677,224,1002,223,2,223,1006,224,659,101,1,223,223,107,226,226,224,102,2,223,223,1005,224,674,101,1,223,223,4,223,99,226 diff --git a/day5/src/main.rs b/day5/src/main.rs new file mode 100644 index 0000000..c84646a --- /dev/null +++ b/day5/src/main.rs @@ -0,0 +1,29 @@ +use icc; + +fn main() { + let contents = std::fs::read_to_string("input") + .expect("Failed to read file 'input'"); + let it = contents.split(","); + let mut program = Vec::new(); + for val in it { + if val.ends_with('\n') { + let mut s = String::from(val); + s.pop(); + program.push(s.parse::().unwrap()); + } + else { + program.push(val.parse::().unwrap()); + } + } + + // Create a copy of the memory to refresh from + let backup = program.clone(); + + let mut output: i32 = 0; + println!("Start part 1"); + icc::simulate(&mut program, 1, &mut output); + + program = backup.clone(); + println!("\nStart part 2"); + icc::simulate(&mut program, 5, &mut output); +} diff --git a/day6/Cargo.lock b/day6/Cargo.lock new file mode 100644 index 0000000..a16c0bf --- /dev/null +++ b/day6/Cargo.lock @@ -0,0 +1,7 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "day6" +version = "0.1.0" diff --git a/day6/Cargo.toml b/day6/Cargo.toml new file mode 100644 index 0000000..89d04ae --- /dev/null +++ b/day6/Cargo.toml @@ -0,0 +1,8 @@ +[package] +name = "day6" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] diff --git a/day6/input b/day6/input new file mode 100644 index 0000000..d584dfe --- /dev/null +++ b/day6/input @@ -0,0 +1,1805 @@ +P1T)TR7 +3NS)SL6 +JMH)MLH +K57)Z9Q +F4G)TCS +LLY)5D3 +6KR)J86 +SH2)TMQ +5WZ)Z2M +ZLL)XYP +F4R)NT5 +36G)8KS +7LB)YRG +V9L)585 +22Y)KT1 +5DN)KY3 +Q2W)YNJ +VRK)FVT +ZL3)59Z +75K)QC8 +GPB)5V8 +S4B)N8N +WQG)4R7 +HJ1)PYT +LD6)ZPY +72F)42V +GP3)GSX +QJV)RJZ +S88)3B1 +Q7Y)T1L +JL9)2CN +CVS)BZH +7DF)5T6 +Z4G)5SD +XHJ)SN3 +XF7)J8C +K3P)6S7 +JLM)7KS +6JS)75X +12Y)CRB +5GS)71S +2BW)RT5 +X7F)1VJ +H9T)L2K +WKY)YPH +Z3X)MT5 +R83)HYS +7QY)YQV +LMD)SAN +SD3)C8V +44R)ZJG +78Y)X4F +NQP)9P4 +GQG)MRV +1ZK)1W6 +LWY)Z9M +NBS)8G7 +VTV)1ZK +L77)DDQ +Y9H)8KD +DTL)T6T +MCC)3ZX +7J3)YMZ +XS1)26Z +V2F)ZQ6 +68X)Z7N +F4G)283 +BX7)495 +CH1)7K3 +R2N)S99 +1T4)B4F +177)8W7 +N7L)3T4 +97G)F7W +QMJ)K3N +TTK)ZTW +NQN)698 +YQ3)R83 +TN1)76X +ZS3)89H +46Y)3ZR +56V)7V7 +J3J)5L4 +31N)NRZ +MJC)NFJ +8HB)S4W +L8N)YNH +MXB)B9J +Z12)7LB +7YP)M93 +4JP)FH2 +5QN)4SH +H2F)GWK +9JF)M3J +ZZJ)X6Y +PCL)J91 +FZM)LWX +9N5)2KQ +VLQ)KD2 +N9B)STL +M9G)DYV +NFJ)R78 +PZ1)R1Q +JMM)RJJ +NM8)KTH +V48)Q2C +QX7)9MB +SCG)JPR +N1G)96H +8BD)BSH +PMS)75K +J2S)ML9 +L32)29L +TQS)VN8 +ZJG)1M7 +PT2)JWZ +7Q4)PVJ +38Z)TD4 +LJM)676 +VRK)Y9H +ZLZ)KF2 +HYW)XCM +L3Z)M3M +9H7)FDW +BYQ)C9Z +4H9)PHX +TLQ)Z99 +7WW)BNC +NS4)TS7 +CF8)PMS +BHJ)19P +CT8)4Z5 +GDR)61S +Y46)36B +FM3)565 +5PQ)VMG +JQ4)PSS +QLT)2MX +975)DPS +DYC)XS3 +Y11)SD3 +YL4)9W9 +SDH)YFD +96R)X23 +92D)VZG +V7G)954 +CJ3)Y8F +GRY)45K +Z78)VM1 +CRB)2J3 +PTK)39Z +C8D)2VY +4R7)16Z +HQM)SCG +Y82)SC1 +CRG)RKZ +YSC)DWW +VH6)QX7 +GWK)WM2 +1W6)PWJ +LWG)B4K +B7Z)5GS +MS8)5FK +QY6)F5G +QB3)5R5 +TXR)V96 +QL6)PV7 +D5M)145 +K27)WTX +LB7)8BC +J1Q)V49 +RWL)SQ6 +B4K)M5T +Y1D)5QL +BJ6)4RP +BXH)QM7 +MPT)BVQ +G56)9V7 +NYP)9C5 +SDK)95K +1BX)3F8 +15N)4VQ +4V7)Z2W +S7Q)PDS +RM4)FYP +ZW3)7D9 +Z9Q)K7G +YKF)9TB +JG9)Y1R +VMD)NQP +5B4)WQ2 +D5J)63S +VKJ)MC9 +3RN)32K +BRK)PXV +P59)VKZ +PSK)6KV +C6N)RHK +11F)RPT +Z8Q)472 +V3D)97S +8J4)1T8 +S8T)W6D +PVJ)FVR +CRB)NDJ +26Z)7GC +YZV)4J8 +6BK)9S6 +5SD)VZB +FM7)L76 +QG6)XZM +DDQ)46Y +WNK)F4G +W1R)L1Q +T1M)S9Q +GWP)Z59 +9HD)K88 +XKJ)VJS +YG7)BDZ +3T4)CH1 +WTX)FM7 +31W)TP6 +7ZN)TH2 +D1Q)MVY +Y9Y)K93 +VN8)75L +VSJ)44R +D95)ZLZ +3YQ)DC3 +T15)HC3 +HRV)K9F +3F8)D5Q +RRF)Z78 +XZM)73S +GBK)82T +HWF)LZ9 +SWS)9LG +TJL)Q5V +MYB)7F1 +3Y8)PV1 +DD6)6HF +X49)C8D +QC8)ZW3 +9MS)9VX +49G)GXH +5W9)4JW +6TS)3W6 +D4P)C12 +BNJ)YTY +3PP)36K +XVV)STY +SL6)TNL +R2B)N3R +RM9)SWS +X8L)WH7 +4SH)1CF +R6P)TRQ +MJM)727 +Q7C)RNF +NT5)F4M +2ST)41Z +T5S)HVK +8KP)P59 +FRK)DR3 +SR2)F4B +BQH)NF6 +SL5)5BB +9V4)K27 +D97)KLS +42B)NS4 +RDN)Y9M +2Q8)H2J +Z6D)GDZ +HTZ)TZX +DB1)5P5 +FVR)Z82 +PD2)L32 +37G)M49 +8PV)6JM +7LJ)8H9 +69P)BXH +ZQJ)924 +HSR)DTJ +WF2)CSV +53J)SJS +L94)QGJ +HX7)K9J +9W9)T2D +YMZ)VD5 +SJV)138 +V9H)JGY +BJW)78V +CZ2)TR8 +MKC)W5R +2CN)YG8 +BFX)7QY +MB1)54Q +SVM)QPT +Z21)R6P +YW4)FJQ +S1W)NM5 +919)975 +RFQ)1JT +53G)6JS +R2B)DLB +8W7)2BW +KLS)4CG +3L6)YJY +56K)5QF +S99)72L +R5G)2QV +C6R)9HD +676)3B5 +8N9)24S +ZYN)ST9 +7TB)S6L +689)MBJ +QGS)XZS +YGH)SRP +865)H27 +YJY)RHY +JTZ)C5T +JZB)6F3 +2Q6)YG7 +6LZ)R9Z +F5G)CQ3 +NK6)N1C +R41)49G +GNC)J8Q +258)X6J +P67)7YX +7J8)PWS +P5B)YW4 +N18)T89 +W67)RFQ +1CV)YBH +Y73)T1Z +JM9)TPJ +RP6)783 +Z4J)LB7 +K3N)4F4 +6JM)NPS +RZD)2ZC +JTZ)QBX +TCS)3LD +HQL)CW5 +J82)XJ3 +6F3)8ZN +NRZ)X27 +4DK)FB1 +339)WFC +973)S4B +D4N)X49 +LWX)FCP +45K)TT6 +F1B)WJF +YPH)ZPJ +BVD)DCC +3FR)5MZ +CR2)3PP +FZG)SNR +18M)RRQ +2PR)C7H +DX6)DJV +VMG)NK2 +843)WLT +MY4)XPZ +QPB)53G +RZH)B2K +13Y)B95 +6LS)1T4 +G9N)F55 +RLR)9R7 +8RV)HCG +73S)K57 +J9N)QD8 +576)QGS +J5Y)4CC +F25)1C6 +52D)BQH +RX4)WVZ +X1Z)BV2 +4ZX)F4P +GMJ)4D7 +JB5)GT7 +KTL)T4S +W8N)XCW +J8Q)N2G +Q98)YRX +WV2)SLL +12T)53K +6S7)CK5 +2RW)WPR +S84)F25 +RV4)PB5 +QZG)15P +8RQ)9KD +Z45)96R +PVJ)F4R +HMT)F54 +96H)4Z8 +TS1)PCL +VS1)G33 +Q6L)JZB +XPM)WF8 +QJF)2YY +PV7)VTV +MSJ)KPJ +RB5)61Z +SFD)TR5 +8CJ)MYB +7HW)DNT +5FK)CPL +2BP)2FK +6D5)48N +83G)956 +8HB)J3F +JGY)XN1 +ZRD)FSF +4CG)VYJ +6QW)FHP +T9P)KW4 +B9J)GF6 +X8C)8J4 +ML7)R4C +W7D)1VB +Q6Q)NQN +Q69)ZYN +53K)5TX +9TB)973 +BSR)HK3 +T8X)GTN +29L)ZRB +GG3)JL9 +WKN)D4N +32K)W69 +JPR)WDB +4H9)PK2 +4BL)X6X +ZXH)KZ7 +WGY)D1N +DF9)49P +KBD)WFB +71S)5B4 +5HC)D9J +SGW)R6R +QSF)D97 +KC4)4B6 +8MN)2T7 +3MC)C6R +CY8)CZ2 +2QR)M2X +6T1)F1B +TFZ)YRV +WGJ)R31 +JW7)HB7 +T9B)GX7 +YG8)W1B +51W)DCP +T89)NY7 +P3G)PCS +GYH)DNM +KN3)27M +VZB)1W8 +Z6S)LD3 +SYN)4D4 +DR3)3FG +QD8)J1Q +PCS)NYP +L65)DN6 +BDN)WGJ +5P5)WD2 +DCC)DKR +Z1Y)6CX +T6L)Y25 +PHX)VKJ +STJ)PGB +HVK)SYM +SLC)56V +CV8)F1D +CK5)R5X +YND)6T1 +11S)Z1Y +MTL)M9M +8XF)D96 +85Z)NSY +TQ9)QR9 +RHY)X8L +TS1)89S +5DN)88C +W3S)GG9 +DTJ)T5Y +YK6)H2M +Z82)J2P +D3G)RL2 +61Z)11F +19Q)ZVW +X6Y)RC3 +NBS)Z69 +1VJ)Q7F +2F4)9M6 +8BD)CBZ +1JT)2ZB +4FG)CJ3 +GG9)177 +36B)T44 +WGV)2ST +H9Y)WV2 +WLN)9MZ +F24)46P +FYP)9DF +N86)6MT +GP3)3YL +F55)CSK +3HH)J1F +Y5V)QQ8 +D3S)K1V +2HC)1H1 +KM9)3WZ +5L8)WXB +TZB)F7H +26G)NK6 +NR1)B3H +GXH)R45 +QFT)DC7 +4TP)71Q +7QY)B5P +F4M)ZNC +PSB)2Q8 +TRQ)N5V +BGZ)4SN +NDP)8KT +S4W)7TQ +9B3)T4T +82T)W47 +NCJ)TFZ +LZQ)T6L +R31)35H +YTY)JS5 +BNJ)1RV +WTB)RV9 +SK4)NLQ +8Q2)SWW +H3X)YNQ +WDX)PD8 +F1J)7JX +Y9Z)VW4 +7K7)MF3 +13R)B8W +4SN)X1Z +5GT)KM9 +PXV)RJK +KF2)9JF +7D5)85C +DQK)B87 +C5T)RP6 +BHL)NM8 +ZQD)287 +6YR)2SY +QSG)H7H +2YY)M62 +C7W)TWW +96K)C97 +3GG)ZZW +CSV)6LS +SJ4)6RQ +15X)X9J +J5Y)8BD +T82)WGY +5WP)72Z +FW2)KN8 +ZRD)2QR +Z2Z)5W9 +K7R)VV3 +MLJ)BDH +G33)LDC +543)15X +P7Z)21Q +T24)WCS +5YC)RCM +PMB)SK4 +YDB)S4M +HVB)R9K +C7Z)LSD +BZ6)LMD +N4M)7K7 +KYB)JMQ +951)DCN +9LG)ZQD +75Q)GHX +3CN)957 +S9Q)KWF +S44)ZRD +JS5)Y66 +MTM)B7Z +Y9M)VLQ +WM6)QV1 +XJB)T5M +PZC)YB8 +HG5)TZ9 +CW5)ZFH +NPS)T82 +JM6)WN8 +KG5)GDR +1RN)N3Y +2YF)FLB +P4X)F74 +NQJ)JXZ +J8C)6V4 +R78)GT3 +CPY)Q8H +NF6)V2F +ZG2)WKY +585)ZXH +P48)339 +ZPY)TJL +CHX)5J9 +YL4)Y73 +H9G)DSC +BDH)G5F +JVQ)S34 +Z3T)NPR +HHK)CL2 +727)576 +72T)CTM +RWD)GQG +CMB)TN1 +BRG)5WP +98Q)Z3T +NF3)JBC +KKB)K9D +T4S)7PW +4XG)GMV +H1B)S5L +J95)HSR +6FL)JDZ +GNK)TTC +VKZ)ZLL +7PW)R2B +DSC)QP2 +QTD)66W +XL2)KN2 +KDT)6SY +RNK)L9H +HWV)V3S +276)8W8 +7VK)RNS +3PM)DYC +WF8)RTT +13M)TZB +TNL)FNP +RNF)RJW +WYF)BRK +Y9P)PZ1 +Q9M)TS1 +JNF)QJF +S79)YFR +K4H)Y82 +LWG)NQ6 +DHH)ZS3 +8G7)S7Q +FJT)HHK +5PK)4S8 +CVR)P12 +R9Z)N9B +17Y)BSR +M7J)7NR +C6R)W1R +Y56)5GT +NT5)XJB +2Q2)SL5 +6NP)S31 +L19)2HC +TVT)415 +3ZH)S93 +91L)39L +FVK)N18 +R67)V8R +TMD)FL5 +4F4)SG2 +XBV)Z18 +GFD)MS8 +9V4)JNC +554)XS1 +9M3)18M +CTQ)HYW +LY4)WTB +HY3)LL3 +2J3)XL2 +VC1)YOU +JMY)RD8 +XK2)D5K +KD2)7J8 +JD1)258 +S1C)SLC +R6R)WXM +6MT)33D +QJB)4TP +287)CSC +FVR)JQ4 +35H)BCS +WQ2)YL4 +DX6)STJ +X42)348 +J3V)XDK +YSM)DZN +6LZ)ZQ8 +HVH)2TR +GB3)Y5V +FHP)Y46 +61S)6LJ +FPK)XTY +P1X)F6N +TZJ)YHR +XHG)N5L +8PS)4ZX +JNC)FFT +412)4XG +YQP)YST +GMJ)SYF +ZJD)FRK +Q23)DTL +V3P)W1H +KMY)H3X +C8K)TJD +WQN)5NY +XZS)3SY +PWJ)Z93 +37Z)BGV +CFQ)72T +GDZ)FCS +82T)WYX +DLH)HQM +MLH)Z8Q +9YV)72F +GX7)CTN +YW4)MJC +RWK)CT8 +2SY)QB3 +16K)MXB +2DQ)LWY +R6R)M4K +BZH)84R +CBZ)L77 +947)WYF +CT8)Q3L +DNM)15N +TX1)VBN +JXZ)3CN +VT4)3WX +3RH)STW +GRB)V7G +8FS)LD1 +3WC)51W +M1D)H9G +TSM)F8F +ZQ6)KDT +F4P)6FD +NK2)NQS +VXV)JFT +C97)C7W +1YR)VMR +YXC)LG6 +STW)17M +1V5)74R +6VZ)S9Z +WV2)SRW +R45)56K +75L)DD1 +7ZV)6LZ +T5M)T15 +RCC)D4P +3W6)5K5 +FBQ)TXR +7V7)VPC +TWW)M2Z +7DF)Z41 +Z31)8HB +M2Z)13M +ZZW)Q9M +5XZ)CZF +BFX)JG9 +ZSH)CMC +D36)CY1 +MWD)8CJ +W6D)TVT +39Z)HVH +9CG)XKJ +XJ3)3PM +84R)N9C +1C8)2NW +DC3)ZJP +P67)947 +7GT)NVV +J91)MWD +R9Z)NKQ +415)8VG +T6T)B4L +6J7)F1J +QBX)ZJD +4XC)CVS +3ZM)D1K +NQJ)BGQ +J2P)4QZ +RGW)GB3 +8KD)37Z +56P)S8T +711)KBM +QL5)4H9 +GP9)SH2 +DKR)ZPS +F4R)K5L +54Q)P1P +6L1)NZR +RPT)9CG +G8S)6QW +4JW)KB5 +ZTK)F24 +SWW)GBK +B7V)J5C +Z6S)PD2 +N9S)CF8 +8BC)Q69 +283)543 +TMD)7LC +QV1)RDN +6FD)KKB +BTS)2WG +3ZR)CY5 +5TX)ZKY +9NL)KB8 +97T)GMJ +68B)GRF +FVC)DW2 +L7D)RYL +RL3)B4C +7YX)JJX +NCX)X21 +BJ8)GPB +YST)ZZ1 +MCS)3Z7 +ZXG)FZY +RYL)4Q9 +5NY)GTK +YQ1)T9P +CF6)46K +F7W)WQG +77Z)CY8 +6W2)HJ1 +TT6)R5K +F68)W3S +DSD)VR2 +JWZ)8FS +YSQ)W67 +J8D)W1P +6KV)BX7 +ZRB)WT8 +3B1)RHJ +2FK)K3P +Q49)ZYK +8DN)9CR +SBT)GL4 +HK3)4XL +FFH)X2T +VWG)VZL +954)J78 +2MX)CYB +JM6)S1W +LRZ)SVM +H1F)9YV +C12)FSH +D9J)CTH +9LV)S3K +RJK)DZ7 +5HZ)9WL +ZKK)K4H +TH2)8QQ +P12)QJV +2HT)Z31 +7K3)WZ5 +3C4)TZK +66D)Q7C +TQ1)7GT +2MX)GRY +LQ1)7LJ +46P)YL8 +6SY)2VR +Y6Q)VP8 +YNQ)LRZ +DKS)MKC +Z69)D9N +V96)DGD +YN9)XKF +KF1)JR4 +LW6)W9S +31W)S55 +J1F)WR4 +3ZX)JW7 +4CC)V53 +SJ4)GQC +BXM)VC1 +PV1)JJF +5F3)G28 +WC1)XPM +KY3)78Y +B4C)9YW +8KS)M6N +ZTW)554 +ZSS)SLS +GNW)KC4 +4S8)Y1N +7TR)4V7 +C7H)3RD +LSD)T9B +VQG)11S +PSS)Z12 +MRV)RB5 +WS6)NQ5 +SBS)711 +42N)3RN +CLL)TX1 +K5S)32G +VR2)7S9 +NPR)12Y +924)NCK +BYX)NR1 +Y6D)7D5 +23G)6BT +N9C)W6X +K52)FZM +5NP)ZJB +Q37)R2N +JZY)66D +NZJ)Q23 +WK9)YN9 +S27)D5M +Y1N)WJK +CJ4)5YC +LDC)N86 +LJM)69P +6BT)R5V +LL3)RYK +PMJ)3PF +S44)TZD +D3D)VMD +D1K)4BL +WR4)MB1 +GF6)J9D +9KV)5H7 +SFM)ZPF +KZ7)S79 +DRJ)ZL3 +MFQ)CMB +4XL)ZG2 +SYM)7YP +FH2)K6Q +PVB)LK7 +BVQ)J95 +9S6)GYH +VMR)PMJ +LPK)9NL +MXC)6J7 +K93)ZGG +MDK)GNK +C9L)56Q +46K)H1Z +FTB)3DY +6CX)X9Z +CB6)2YF +SNR)NF3 +J78)XHJ +9V7)R54 +3LD)S1C +M4K)WF2 +TRQ)MHC +BGV)CR2 +LLN)2DY +NQ6)F8B +F6N)31N +74N)TZZ +YHR)M72 +BF6)1YR +7LG)P6F +KTH)X28 +4ZT)T11 +S55)Q98 +PB5)J3V +YG8)X8C +DPM)HW6 +KW4)4HL +ZMY)P4S +J3F)Z2L +NSY)9WX +YVM)XDF +CL2)85Y +K5L)RNK +J2K)1KC +VV3)V4L +Y88)7XT +F4N)ZVH +6HF)NZJ +3WZ)N7L +GV5)M7J +KPJ)7XK +S9Q)MQ5 +Q3L)TP5 +6HF)RVK +ZR1)P5B +JMQ)QL5 +R5Y)LHV +RMD)38Z +VKP)8MN +XPZ)J82 +CR3)61H +R1Q)DD6 +N5L)RLR +FFT)LPK +WM2)WC4 +HG2)QNN +S34)SJV +X4F)MTL +SLS)82Q +32G)TTK +J9M)YXC +R9K)P6T +BNC)MPT +3B5)VS1 +VZH)SGW +MJM)334 +8PS)WGD +S5L)D1Q +138)GBT +VTJ)JMM +ZJP)C85 +FZY)W4B +SHW)3WC +DB1)TQS +9VX)19Z +CF8)HQL +WYX)Z4G +J1J)Q37 +Z75)P3V +PGB)77Z +1C6)SJX +XPG)Q84 +4F1)M9G +D4N)JMD +7JX)Q4X +BMG)V33 +J86)JD1 +KN2)KBD +B87)XDJ +VYJ)4FG +XDF)7ZN +HLF)YQP +7YP)PSB +WRK)6FL +QNN)PL6 +BP7)QW9 +DMQ)BJ8 +Q5V)N4M +XS3)CF5 +WXB)C9Q +P4S)8WW +Z8V)53J +SLL)TQ9 +71Q)Q6Q +3H4)CVR +XHJ)X4Q +3SY)DHH +5W7)DFV +9MB)HY3 +61H)H14 +JR4)ZGR +FDW)11Z +V3H)H7D +R5K)KH2 +KFK)ZVL +CQ3)Y5S +W6X)16K +BSW)FKY +TMQ)1T2 +S4M)BP7 +C9Z)L2J +GRF)Z6D +1T8)2DQ +D97)WHF +ZST)9R5 +VZG)CTQ +CB6)PZC +ZTY)TVW +ZGR)8XF +41Z)F9Y +Q8H)SHW +WVZ)KB6 +3PF)7QD +BDZ)YVM +W1H)7ZV +F5G)DR7 +NM5)3MT +72L)G62 +1H1)68B +WN8)Q2W +9M3)756 +5H7)1RN +DGD)RGQ +DLB)5VL +HZV)VKP +7X3)4WP +NZR)TLD +21Q)MLL +X77)4JP +5R5)7DQ +X28)Y1Q +YRV)BJW +M14)6KB +VZL)FBQ +WD3)CV8 +J9R)KWG +C3G)Y74 +P5B)BHL +HHN)WD3 +FNP)KTL +QGJ)P9B +B6G)9H7 +YFR)919 +FVX)M74 +7XK)V3H +ZVH)ZZJ +TSH)6NP +63H)M1K +W4C)RZH +ZZ1)P48 +QGS)69H +5J9)YDB +S8L)P4X +TP6)MJM +JJF)Z3L +KN2)P7Z +CPK)H1B +3SN)WKF +DCC)F4W +5H6)2F4 +MVY)412 +NRL)GP3 +T44)F4N +T8X)Z3X +8LZ)GR6 +8KT)Q4C +M74)MCC +2L9)S27 +36K)G2N +957)WS5 +TXR)7VJ +B95)ZJR +K9J)BM9 +ZVL)CGZ +7QD)P8Y +ZYK)239 +XTY)YSM +4VQ)MYM +SLZ)YGH +L76)ZB9 +DDQ)MNC +P9B)WQN +DW2)H9Y +WKF)W37 +48V)FHH +76X)3FR +TZZ)8RQ +YDS)NBJ +R4C)C1Q +258)7WF +B3H)TSM +4Z1)L98 +C8V)9NJ +ZKY)D3G +J3G)7Q4 +XN1)S88 +RJZ)6KR +YFD)GSS +8H9)WLN +TTW)D95 +F7H)J9R +H7D)Z2Z +Y25)Q6L +PDC)FZG +783)7TR +8M9)FPK +2GT)PSK +XZG)42B +1KC)PTK +TVK)BHJ +TVH)XMK +2KQ)DPF +ZNC)7DF +VJS)5NP +RV9)375 +RWY)31W +3RS)J5Y +SHF)Y88 +PWS)J2K +VK8)9B6 +J1F)WS6 +5V8)Y9Y +RC3)L7D +2YF)K52 +VV3)TZN +6KB)P78 +7BP)CF6 +R5V)GJS +B2K)CR3 +8MX)LWG +YG7)NND +SD3)PVB +CHP)NLM +HYS)19Q +T2D)D6H +SQ6)BYX +NVV)C3G +TVW)L19 +8W8)SBZ +3Y4)L5V +L2S)XHG +QM7)WQS +239)NCJ +DHH)S2P +1W8)13R +NQ5)7LT +RJK)9J3 +CMK)YRY +STL)5L8 +RYJ)SG8 +3Z7)9V4 +46Y)C6N +GFH)QZG +CMC)FJT +81H)DRJ +L94)8DW +W1X)2P4 +9VT)DF9 +X9J)N9S +CYB)H1F +SJX)VQG +4RP)WM6 +HYW)1C8 +XMJ)Y6Q +TR5)5XZ +LS7)91J +CXM)276 +WH7)BJ6 +FRD)7X3 +BCS)K46 +FKY)BXM +TBN)4Z1 +54B)99H +2B9)JXH +DWW)WL5 +ZS3)SR2 +MDR)DDS +KJD)LZQ +WBM)HX7 +KDP)T5S +2WG)BF6 +RFJ)L65 +3N4)KLK +Q7F)5WZ +K4P)P67 +SS1)PT2 +LV4)11L +8VG)HZV +GL4)BSW +7LC)QSF +RNS)23G +FCS)XLB +LHV)B8K +MD3)8M9 +YRG)SBS +3MP)FXS +Z75)T1M +RRQ)VXV +LD1)7LG +ZFB)Z42 +56J)Q7Y +8ZQ)R43 +N3R)5HC +Y1R)2RW +GMZ)6MN +ZQ8)6YR +GQC)WDX +RD8)D5J +HCG)Y11 +NCK)2L9 +911)Z16 +G81)CJ4 +NTY)3NS +SBZ)HG2 +2VR)SBT +WYX)NQJ +6QQ)6NT +P1P)1CV +CGZ)V48 +RTT)5H6 +7D9)KMY +VTV)54B +F74)FT6 +KB8)RZD +3MT)JWC +56Q)H9C +RHK)865 +XCM)ZQJ +T5Y)GNC +W9S)ZFB +9WL)GV5 +DN6)RX4 +SG8)NCX +P3V)7WW +B8K)8PS +78V)VWZ +FSH)VT4 +KH2)BQP +DJV)N2D +WT8)BVM +ZB9)ZMY +CTH)YKB +24S)FGH +FBQ)7VK +C85)V3D +PK2)RWD +BQP)W84 +H1Z)DNQ +VP8)K4P +DZ7)XPG +45R)PDC +SG5)52G +69H)RM4 +DR7)9M3 +X23)TLQ +VPC)ZQR +5SL)97P +Z59)9LV +JJX)HRV +J9D)Q4S +RJW)WKN +6RQ)QLT +TLR)LLY +KBM)13Y +L9H)952 +XDJ)3RS +JFT)Q1Z +NJ6)XVV +FL5)5TK +L1Q)TK3 +PDS)X7F +5BB)QZB +1RV)154 +PWJ)LZ4 +QPT)5DN +N9C)RCC +DLH)NRL +Z9M)2Q2 +FXS)66F +ZSD)R5G +GMZ)1G1 +K6Q)YQ1 +QHH)SHF +WD2)GFH +MYM)ZP3 +5QF)LQ1 +N2G)C35 +MLL)5QY +JW7)QY6 +X4Q)81H +97S)1L9 +S4G)5QN +9DF)6BG +LMD)HLF +VBN)VHW +4JP)Z13 +ZTW)J8D +V8R)7Q9 +5HZ)2B9 +WV7)K7R +DYV)KJD +1VB)VNX +16Z)52D +M74)J1J +L7D)D3D +D1N)RFJ +GX7)6MS +19Z)H99 +COM)RV4 +B5P)SDH +W1P)M33 +DC7)SQ7 +BTS)85Z +88C)T24 +NDJ)KG5 +4HL)KF1 +M5T)MDS +4YY)GRB +C1Q)K9V +TBN)Y56 +WS5)W1X +BBX)Z8G +XWS)6TS +7DQ)2HT +698)MXC +KV9)CB6 +TD4)S4G +B7Z)H4Q +7D9)DWX +Z3L)2PR +S9Z)2BP +YQF)YND +G62)3Y4 +VNX)GMZ +T6L)S8L +Z13)Z21 +WQS)JM9 +5J8)M14 +15P)8ZQ +CPL)DYL +PL6)R5Y +L8N)MFQ +89H)6W2 +JBC)LW6 +ZP3)XP5 +T2D)G56 +TLD)ZSS +M3J)WK9 +85Y)D5R +FNG)BZ6 +74R)RMD +48N)TZJ +RJJ)ZJV +V4L)M1D +SN3)JZY +85D)1FQ +CY5)SDK +7WW)741 +2KQ)G8S +91J)L8N +LQ1)JHC +66W)Y9Z +GNC)FXP +Z7N)V97 +ZM5)92D +XDK)911 +M6N)W82 +95K)LS7 +VBN)TLR +TK3)TVH +NBJ)45R +1K7)M7X +S31)P3G +WBM)2V5 +7LT)LLN +9NJ)9VT +MLL)SFM +3DY)L3Z +348)S44 +N8N)YSC +5T6)JB5 +2VY)93L +D96)LV4 +SG2)YKF +YB8)LY4 +96H)RGW +W4B)X6N +5L4)KV9 +YQV)GWP +TWX)3MP +H99)DSD +WFB)7J3 +C5T)3MC +6F9)1YX +DWX)XTR +7WF)SFJ +Q1Z)8N9 +YMZ)ZSD +11L)T23 +6LV)W2B +PXS)K6M +952)BYQ +WL5)H9T +GLK)1V5 +XLB)Z75 +4LC)TTW +Y77)FRD +P4X)9W8 +TZ9)JDT +KWG)SG5 +T15)FM3 +2CZ)W8N +4Q9)MCS +K9F)HTD +GTK)B6G +741)VZH +4D4)4YY +9S6)6SG +FGH)GNW +X21)QL6 +W1R)JM6 +89S)JMH +9R5)96K +H2J)C9G +9WX)J9M +WXM)XWS +MQ5)3Q8 +XMK)Z6S +472)FVX +7Q9)QSG +J5C)5GZ +FVT)MTM +M49)85D +13N)BFX +TJD)RM9 +SYF)SJ4 +S3K)9MS +V3S)ZXG +3YL)3HH +ML9)6F9 +BGQ)WC1 +NLM)KDP +2ZC)7TB +F8B)83G +4QZ)Y6D +MZ4)1JW +6V4)YK6 +FCP)QJB +Q84)GP9 +TZK)91L +TS7)4NJ +7VJ)5PQ +B8K)C8K +T4T)B7V +2NW)843 +HNP)PXS +B5P)9KV +XTR)Q49 +FSF)RWK +WGD)ZTY +GLK)RWY +TTC)J2S +ZVW)DQK +R5X)YDS +NNW)ZM5 +K6M)4ZT +QR9)2GT +Q4C)BDN +S2P)22Y +T23)SFD +8KS)RYJ +7TQ)1PP +KPL)48V +D5Q)BMG +1RN)41Q +W5R)8BB +5VL)HTZ +B4F)HG5 +ZJR)R41 +2TR)5PK +JP3)NLZ +59Z)NBS +FJQ)VSJ +DPS)HMT +4D7)TBN +1G1)MLJ +P7T)65X +SDH)W7D +WYF)KN3 +S6L)HWF +DCP)TVK +LK7)W4C +GT7)ZNS +ZJV)TKJ +ZPJ)Y9P +33D)TQ1 +2QV)Y77 +XCW)4DK +NQ6)3Y8 +72Z)8PV +YL8)YCD +JHC)6QQ +F54)DPM +YQ1)5NR +9W8)BNJ +GSS)JNF +V49)BGZ +S4B)DMQ +9CR)1BX +C35)GFD +KFK)YQF +JD7)46T +Z16)J3G +SWW)CFQ +K46)ZSH +154)8KP +Q4X)8RV +KWF)5HZ +NKQ)T8X +M4F)DB1 +YL8)8Q2 +27M)YQ3 +49P)TFC +956)X42 +JWC)FW2 +YXF)H2F +FLB)P1X +GSX)81F +XTR)26G +88W)3SN +8DW)FFH +W84)BS6 +Z2L)YSQ +X9Z)4LC +YRY)3ZM +CF5)97G +31Z)FTB +VHW)YXF +MPT)DNF +G5F)DLH +VM1)BRG +Q4S)ML7 +ST9)JP3 +XMK)P7T +83G)WGV +ZNV)P1T +TKJ)63H +6NT)QMJ +SH2)FVC +W1B)Z4J +1M7)PMB +9W8)31Z +R83)WV7 +MC9)PX3 +ZGG)QPB +1L9)4XC +DPF)RL3 +F8F)C45 +PYT)YVL +9MZ)74N +59Z)3RH +MHC)8SM +SFJ)SLZ +R43)8W5 +7KS)J6V +N3Y)3R8 +L2K)WNK +9P4)XF7 +DNF)377 +XYP)3GG +QZB)1K7 +GMV)N1G +6SG)YZV +P8Y)XBV +GPT)S7K +Q5V)KYB +X27)4JC +756)M4F +FT6)JD7 +RHJ)98Q +FXP)7HW +XFS)HWV +C9G)689 +Y1Q)J9N +46T)JLM +J86)S84 +BM9)NJ6 +F4B)VWG +GF2)VRK +W82)56J +JXH)3C4 +VXV)R67 +WCS)C9L +5TX)CMK +Z41)L2S +RVK)TSH +M7X)Y1D +TZN)73T +JVN)FRX +P6T)3YQ +M33)VH6 +YRX)VK8 +93L)6LV +ZFH)X77 +GTN)TWX +S93)NDP +LZ9)12T +WHF)3ZH +H4Q)8DN +Z42)17Y +HW6)V9H +NQS)3N4 +1PP)MD3 +CZF)BVD +TP5)56P +M72)XK2 +CSC)LTB +8QQ)ZTK +TZX)XMJ +YNQ)C7Z +WJF)37G +5QY)ZR1 +WFC)D3S +YVL)QZC +SRW)5SL +KYB)G81 +6LJ)8JZ +NCK)JVQ +KB6)GF2 +9YW)CLF +9M6)6L1 +F1D)ZKK +7S9)DLM +Y5S)68X +C9Z)K5S +L98)CCR +RCM)2Q6 +8H9)7BP +4Z5)KFK +CTN)NNW +LV4)97T +1C8)VBZ +GBK)QHH +3YL)ZST +M1W)6D5 +MNC)42N +D6H)DKS +VKJ)5W7 +FRX)CHP +NY7)8LZ +Z2W)MZ4 +DFV)TMD +K9V)HNP +K88)3H4 +F4W)V9L +QQ8)2CZ +MBJ)GPT +M2X)Z8V +3Q8)GG3 +RL2)4F1 +81H)WRK +3WX)GQ2 +WDB)BBX +JMD)J3J +HC3)9B3 +CLF)G9N +SL5)LD6 +5F3)MDK +X6N)JVN +B4L)HHN +YPT)F68 +B8W)5F3 +N1C)DX6 +WLT)88W +Y66)D36 +X6J)XZG +CMC)36G +T1Z)3L6 +ZPF)JTZ +C45)MY4 +QPT)YPT +5QL)9N5 +LD3)LJM +TFC)RWL +YQV)CPY +85C)75Q +TR7)CLL +TZZ)ZNV +NND)GLK +GQ2)WBM +QP2)L94 +WJK)HVB +3R8)QG6 +7NR)6BK +2V5)V3P +LZ4)CHX +M3M)NTY +3FG)5J8 +BSH)Z45 +1BX)MSJ +S7K)HF8 +Z93)BTS +5VL)SYN +CTM)MDR +YNJ)951 +D5K)CXM +JDZ)XFS +4CC)FVK +D9N)KPL +4J8)CRG +YBH)QFT +W47)QTD +XYP)13N +8SM)SS1 +MT5)VTJ +2ZB)6VZ +SC1)FNG +4Z8)RRF +XKF)M1W +5NR)CPK +ZPS)JMY +RHJ)8MX diff --git a/day6/src/main.rs b/day6/src/main.rs new file mode 100644 index 0000000..4dbc3ce --- /dev/null +++ b/day6/src/main.rs @@ -0,0 +1,169 @@ +use std::collections::HashMap; + +fn copy_to_array(a: &mut [char; 3], b: &str) { + assert_eq!(b.len(), 3); + let mut x = 0; + for c in b.chars() { + a[x] = c; + x += 1; + } +} + +fn main() { + { + let test_map = get_map_from_file("test"); + assert_eq!(test_map.get("COM").unwrap().distance_to_com(&test_map), 0); + assert_eq!(test_map.get("B").unwrap().distance_to_com(&test_map), 1); + assert_eq!(test_map.get("D").unwrap().distance_to_com(&test_map), 3); + assert_eq!(test_map.get("L").unwrap().distance_to_com(&test_map), 7); + let f_parents = test_map.get("F").unwrap().parents(&test_map); + assert_eq!(f_parents, vec!["E", "D", "C", "B", "COM"]); + let l_parents = test_map.get("L").unwrap().parents(&test_map); + assert_eq!(l_parents, vec!["K", "J", "E", "D", "C", "B", "COM"]); + assert_eq!(first_common(f_parents, l_parents), "E"); + let mut x: i32 = 0; + for val in test_map.values() { + x += val.distance_to_com(&test_map); + } + assert_eq!(x, 42); + } + + { + let test_map2 = get_map_from_file("test2"); + let you = test_map2.get("YOU").unwrap(); + let san = test_map2.get("SAN").unwrap(); + println!("{:?}", you); + println!("{:?}", san); + println!("{:?}", you.parents(&test_map2)); + println!("{:?}", san.parents(&test_map2)); + let parent = first_common(you.parents(&test_map2), san.parents(&test_map2)); + println!("First common parent of YOU and SAN: '{}'", parent); + println!("Distance from YOU to {}: {}", parent, you.distance_to(&parent, &test_map2)); + println!("Distance from SAN to {}: {}", parent, san.distance_to(&parent, &test_map2)); + + println!("[Test2] Transfers required to go from YOU to SAN: {}", + you.distance_to(&parent, &test_map2) + san.distance_to(&parent, &test_map2) - 2); + } + + let map = get_map_from_file("input"); + let mut x: i32 = 0; + for val in map.values() { + x += val.distance_to_com(&map); + } + println!("[Part 1] Total indirect and direct orbits: {}", x); + + let you = map.get("YOU").unwrap(); + let you_parents = you.parents(&map); + let san = map.get("SAN").unwrap(); + let san_parents = san.parents(&map); + let common_parent = first_common(you_parents, san_parents); + println!("First common parent of YOU and SAN: '{}'", common_parent); + println!("Distance from YOU to {}: {}", common_parent, you.distance_to(&common_parent, &map)); + println!("Distance from SAN to {}: {}", common_parent, san.distance_to(&common_parent, &map)); + println!("[Part 2] Transfers required to go from YOU to SAN: {}", + you.distance_to(&common_parent, &map) + san.distance_to(&common_parent, &map) - 2); +} + +fn first_common(a: Vec, b: Vec) -> String { + let mut x: Option = None; + for v_a in a.iter() { + let mut iter: usize = 0; + for v_b in b.iter() { + if v_a == v_b { + x = Some(iter); + break; + } + iter += 1; + } + if x.is_some() { + break; + } + } + return b[x.unwrap()].clone(); +} + +fn get_map_from_file(file: &str) -> HashMap { + let contents = std::fs::read_to_string(file) + .expect("Failed to read file 'input'"); + let it = contents.split("\n"); + let mut map: HashMap = HashMap::new(); + for line in it { + let s = String::from(line); + s.trim(); + if s.is_empty() { + break; + } + { + let values: Vec<&str> = s.split(")").collect(); + //println!("Line: {}", line); + assert_eq!(values.len(), 2); + //assert_eq!(values[0].len(), 3); + //assert_eq!(values[1].len(), 3); + for v in values { + if !map.contains_key(v) { + let n = Node { + id: v.to_string(), + parent: None, + children: Vec::new(), + }; + map.insert(v.to_string(), n); + } + } + } + let values: Vec<&str> = s.split(")").collect(); + { + let mut node = map.get_mut(values[1]).unwrap(); + if !node.parent.is_some() { + node.parent = Some(values[0].to_string()); + } + } + { + let mut node = map.get_mut(values[0]).unwrap(); + if !node.children.contains(&values[1].to_string()) { + node.children.push(values[1].to_string()); + } + } + } + return map; +} + +#[derive(Debug)] +struct Node { + parent: Option, + id: String, + children: Vec, +} + +impl Node { + + fn distance_to(&self, to: &str, map: &HashMap) -> i32 { + if self.id == to { + return 0; + } + let parent = self.parent.as_ref().unwrap().clone(); + return map.get(&parent).unwrap().distance_to(to, map) + 1; + } + + fn distance_to_com(&self, map: &HashMap) -> i32 { + return self.distance_to("COM", map); + } + + fn parents(&self, map: &HashMap) -> Vec { + let mut parents: Vec = Vec::new(); + if self.parent.is_some() { + parents.push(self.parent.as_ref().unwrap().clone()); + let parent = map.get(&self.parent.as_ref().unwrap().clone()).unwrap(); + for v in parent.parents(map) { + parents.push(v); + } + } + return parents; + } + +} + +impl PartialEq for Node { + fn eq(&self, other: &Self) -> bool { + self.id == other.id + } +} diff --git a/day6/test b/day6/test new file mode 100644 index 0000000..183242d --- /dev/null +++ b/day6/test @@ -0,0 +1,11 @@ +COM)B +B)C +C)D +D)E +E)F +B)G +G)H +D)I +E)J +J)K +K)L diff --git a/day6/test2 b/day6/test2 new file mode 100644 index 0000000..a1007c6 --- /dev/null +++ b/day6/test2 @@ -0,0 +1,13 @@ +COM)B +B)C +C)D +D)E +E)F +B)G +G)H +D)I +E)J +J)K +K)L +K)YOU +I)SAN diff --git a/day7/Cargo.lock b/day7/Cargo.lock new file mode 100644 index 0000000..2b9779a --- /dev/null +++ b/day7/Cargo.lock @@ -0,0 +1,30 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "day7" +version = "0.1.0" +dependencies = [ + "icc", + "itertools", +] + +[[package]] +name = "either" +version = "1.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e78d4f1cc4ae33bbfc157ed5d5a5ef3bc29227303d595861deb238fcec4e9457" + +[[package]] +name = "icc" +version = "1.0.0" + +[[package]] +name = "itertools" +version = "0.10.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a9a9d19fa1e79b6215ff29b9d6880b706147f16e9b1dbb1e4e5947b5b02bc5e3" +dependencies = [ + "either", +] diff --git a/day7/Cargo.toml b/day7/Cargo.toml new file mode 100644 index 0000000..4c058ed --- /dev/null +++ b/day7/Cargo.toml @@ -0,0 +1,10 @@ +[package] +name = "day7" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +icc = { path = "../icc", version = "1.0.0"} +itertools = "0.10.3" \ No newline at end of file diff --git a/day7/src/#main.rs# b/day7/src/#main.rs# new file mode 100644 index 0000000..7599d41 --- /dev/null +++ b/day7/src/#main.rs# @@ -0,0 +1,132 @@ +use std::collections::VecDeque; +use itertools::Itertools; + +fn main() { + let program = vec![3,8,1001,8,10,8,105,1,0,0,21,38,63,88,97,118,199,280,361,442,99999,3,9,1002,9,3,9,101,2,9,9,1002,9,4,9,4,9,99,3,9,101,3,9,9,102,5,9,9,101,3,9,9,1002,9,3,9,101,3,9,9,4,9,99,3,9,1002,9,2,9,1001,9,3,9,102,3,9,9,101,2,9,9,1002,9,4,9,4,9,99,3,9,102,2,9,9,4,9,99,3,9,102,4,9,9,101,5,9,9,102,2,9,9,101,5,9,9,4,9,99,3,9,1002,9,2,9,4,9,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,3,9,101,1,9,9,4,9,3,9,101,2,9,9,4,9,3,9,1001,9,2,9,4,9,3,9,102,2,9,9,4,9,3,9,102,2,9,9,4,9,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,99,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,3,9,1001,9,2,9,4,9,3,9,1001,9,2,9,4,9,3,9,1001,9,1,9,4,9,3,9,1001,9,1,9,4,9,3,9,1001,9,2,9,4,9,3,9,102,2,9,9,4,9,3,9,1002,9,2,9,4,9,3,9,1001,9,1,9,4,9,99,3,9,1002,9,2,9,4,9,3,9,1002,9,2,9,4,9,3,9,102,2,9,9,4,9,3,9,1002,9,2,9,4,9,3,9,1001,9,1,9,4,9,3,9,102,2,9,9,4,9,3,9,102,2,9,9,4,9,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,3,9,102,2,9,9,4,9,99,3,9,102,2,9,9,4,9,3,9,101,1,9,9,4,9,3,9,1002,9,2,9,4,9,3,9,1002,9,2,9,4,9,3,9,102,2,9,9,4,9,3,9,1002,9,2,9,4,9,3,9,1001,9,2,9,4,9,3,9,101,2,9,9,4,9,3,9,1001,9,2,9,4,9,3,9,101,1,9,9,4,9,99,3,9,101,1,9,9,4,9,3,9,101,1,9,9,4,9,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,3,9,1001,9,1,9,4,9,3,9,1001,9,2,9,4,9,3,9,101,2,9,9,4,9,3,9,102,2,9,9,4,9,3,9,1001,9,1,9,4,9,3,9,1001,9,2,9,4,9,99]; + + let mut max_storage = 0; + let mut max_settings: Vec = Vec::new(); + + { + let settings = vec![0, 1, 2, 3, 4]; + // Cheese. + for permutation in settings.into_iter().permutations(5) { + //println!("{:?}", permutation); + let storage = run_amplifiers(&program, permutation.clone()); + if storage > max_storage { + max_storage = storage; + max_settings = permutation.clone(); + } + } + println!("[Part 1] Settings {:?} produced a value of {}", max_settings, max_storage); + } + + { + let settings = vec![5, 6, 7, 8, 9]; + for permutation in settings.into_iter().permutations(5) { + let storage = run_feedback_amplifiers(&program, permutation.clone()); + if storage > max_storage { + max_storage = storage; + max_settings = permutation.clone(); + } + } + println!("[Part 2] Settings {:?} produced a value of {}", max_settings, max_storage); + } +} + +fn run_amplifiers(program: &Vec, settings: Vec) -> i32 { + let mut storage: i32 = 0; + for setting in settings { + let mut input = VecDeque::from([setting, storage]); + let mut output: Vec = Vec::new(); + icc::simulate(&mut program.clone(), &mut input, &mut output, 0); + storage = output[0]; + } + return storage; +} + +fn run_feedback_amplifiers(program: &Vec, settings: Vec) -> i32 { + let amplifiers = [ + // program, input signal, entrypoint, setting + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + ]; + let mut iter: i32 = 0; + loop { + for (index, setting) in settings.iter().enumerate() { + match amplifiers[index].3 { + icc::Status::Finished => { + if index == 4 { + // the output of amplifier 4 is stored on the input of amplifier 0 + return *amplifiers[0].1; + } + continue; + }, + _ => {} + } + println!("[Iter {}] Running amplifier {} from instruction {}", iter, index, *amplifiers[index].2); + let mut input = if iter == 0 { + VecDeque::from([*setting, *amplifiers[index].1]) + } else { + VecDeque::from([*amplifiers[index].1]) + }; + let mut output: Vec = Vec::new(); + let result = icc::simulate(amplifiers[index].0, &mut input, &mut output, *amplifiers[index].2); + match result.status { + icc::Status::WaitingForInput => { + println!("[Iter {}] Amplifier {} is waiting for input", iter, index); + }, + _ => {}, + } + let amp_index = (index+1) % settings.len(); + *amplifiers[amp_index].1 = output[0]; + println!("[Iter {}] Amplifier {}->{}: {}", iter, index, amp_index, output[0]); + *amplifiers[index].2 = result.instruction; + *amplifiers[index].3 = result.status; + } + iter += 1; + } +} + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn example_1() { + let program = vec![3,15,3,16,1002,16,10,16,1,16,15,15,4,15,99,0,0]; + let settings = vec![4, 3, 2, 1, 0]; + assert_eq!(run_amplifiers(&program, settings), 43210); + } + + #[test] + fn example_2() { + let program = vec![3,23,3,24,1002,24,10,24,1002,23,-1,23,101,5,23,23,1,24,23,23,4,23,99,0,0]; + let settings = vec![0,1,2,3,4]; + assert_eq!(run_amplifiers(&program, settings), 54321); + } + + #[test] + fn example_3() { + let program = vec![3,31,3,32,1002,32,10,32,1001,31,-2,31,1007,31,0,33,1002,33,7,33,1,33,31,31,1,32,31,31,4,31,99,0,0,0]; + let settings = vec![1,0,4,3,2]; + assert_eq!(run_amplifiers(&program, settings), 65210); + } + + #[test] + fn part2_example_1() { + let program = vec![3,26,1001,26,-4,26,3,27,1002,27,2,27,1,27,26,27,4,27,1001,28,-1,28,1005,28,6,99,0,0,5]; + let settings = vec![9,8,7,6,5]; + assert_eq!(run_feedback_amplifiers(&program, settings), 139629729); + } + + #[test] + fn part2_example_2() { + let program = vec![3,52,1001,52,-5,52,3,53,1,52,56,54,1007,54,5,55,1005,55,26,1001,54,-5,54,1105,1,12,1,53,54,53,1008,54,0,55,1001,55,1,55,2,53,55,53,4,53,1001,56,-1,56,1005,56,6,99,0,0,0,0,10]; + let settings = vec![9,7,8,5,6]; + assert_eq!(run_feedback_amplifiers(&program, settings), 18216); + } +} diff --git a/day7/src/.#main.rs b/day7/src/.#main.rs new file mode 120000 index 0000000..2c965d9 --- /dev/null +++ b/day7/src/.#main.rs @@ -0,0 +1 @@ +kienan@monolith.244424:1652264161 \ No newline at end of file diff --git a/day7/src/main.rs b/day7/src/main.rs new file mode 100644 index 0000000..7599d41 --- /dev/null +++ b/day7/src/main.rs @@ -0,0 +1,132 @@ +use std::collections::VecDeque; +use itertools::Itertools; + +fn main() { + let program = vec![3,8,1001,8,10,8,105,1,0,0,21,38,63,88,97,118,199,280,361,442,99999,3,9,1002,9,3,9,101,2,9,9,1002,9,4,9,4,9,99,3,9,101,3,9,9,102,5,9,9,101,3,9,9,1002,9,3,9,101,3,9,9,4,9,99,3,9,1002,9,2,9,1001,9,3,9,102,3,9,9,101,2,9,9,1002,9,4,9,4,9,99,3,9,102,2,9,9,4,9,99,3,9,102,4,9,9,101,5,9,9,102,2,9,9,101,5,9,9,4,9,99,3,9,1002,9,2,9,4,9,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,3,9,101,1,9,9,4,9,3,9,101,2,9,9,4,9,3,9,1001,9,2,9,4,9,3,9,102,2,9,9,4,9,3,9,102,2,9,9,4,9,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,99,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,3,9,1001,9,2,9,4,9,3,9,1001,9,2,9,4,9,3,9,1001,9,1,9,4,9,3,9,1001,9,1,9,4,9,3,9,1001,9,2,9,4,9,3,9,102,2,9,9,4,9,3,9,1002,9,2,9,4,9,3,9,1001,9,1,9,4,9,99,3,9,1002,9,2,9,4,9,3,9,1002,9,2,9,4,9,3,9,102,2,9,9,4,9,3,9,1002,9,2,9,4,9,3,9,1001,9,1,9,4,9,3,9,102,2,9,9,4,9,3,9,102,2,9,9,4,9,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,3,9,102,2,9,9,4,9,99,3,9,102,2,9,9,4,9,3,9,101,1,9,9,4,9,3,9,1002,9,2,9,4,9,3,9,1002,9,2,9,4,9,3,9,102,2,9,9,4,9,3,9,1002,9,2,9,4,9,3,9,1001,9,2,9,4,9,3,9,101,2,9,9,4,9,3,9,1001,9,2,9,4,9,3,9,101,1,9,9,4,9,99,3,9,101,1,9,9,4,9,3,9,101,1,9,9,4,9,3,9,101,1,9,9,4,9,3,9,102,2,9,9,4,9,3,9,1001,9,1,9,4,9,3,9,1001,9,2,9,4,9,3,9,101,2,9,9,4,9,3,9,102,2,9,9,4,9,3,9,1001,9,1,9,4,9,3,9,1001,9,2,9,4,9,99]; + + let mut max_storage = 0; + let mut max_settings: Vec = Vec::new(); + + { + let settings = vec![0, 1, 2, 3, 4]; + // Cheese. + for permutation in settings.into_iter().permutations(5) { + //println!("{:?}", permutation); + let storage = run_amplifiers(&program, permutation.clone()); + if storage > max_storage { + max_storage = storage; + max_settings = permutation.clone(); + } + } + println!("[Part 1] Settings {:?} produced a value of {}", max_settings, max_storage); + } + + { + let settings = vec![5, 6, 7, 8, 9]; + for permutation in settings.into_iter().permutations(5) { + let storage = run_feedback_amplifiers(&program, permutation.clone()); + if storage > max_storage { + max_storage = storage; + max_settings = permutation.clone(); + } + } + println!("[Part 2] Settings {:?} produced a value of {}", max_settings, max_storage); + } +} + +fn run_amplifiers(program: &Vec, settings: Vec) -> i32 { + let mut storage: i32 = 0; + for setting in settings { + let mut input = VecDeque::from([setting, storage]); + let mut output: Vec = Vec::new(); + icc::simulate(&mut program.clone(), &mut input, &mut output, 0); + storage = output[0]; + } + return storage; +} + +fn run_feedback_amplifiers(program: &Vec, settings: Vec) -> i32 { + let amplifiers = [ + // program, input signal, entrypoint, setting + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + (&mut program.clone(), &mut 0, &mut 0usize, &mut icc::Status::Running), + ]; + let mut iter: i32 = 0; + loop { + for (index, setting) in settings.iter().enumerate() { + match amplifiers[index].3 { + icc::Status::Finished => { + if index == 4 { + // the output of amplifier 4 is stored on the input of amplifier 0 + return *amplifiers[0].1; + } + continue; + }, + _ => {} + } + println!("[Iter {}] Running amplifier {} from instruction {}", iter, index, *amplifiers[index].2); + let mut input = if iter == 0 { + VecDeque::from([*setting, *amplifiers[index].1]) + } else { + VecDeque::from([*amplifiers[index].1]) + }; + let mut output: Vec = Vec::new(); + let result = icc::simulate(amplifiers[index].0, &mut input, &mut output, *amplifiers[index].2); + match result.status { + icc::Status::WaitingForInput => { + println!("[Iter {}] Amplifier {} is waiting for input", iter, index); + }, + _ => {}, + } + let amp_index = (index+1) % settings.len(); + *amplifiers[amp_index].1 = output[0]; + println!("[Iter {}] Amplifier {}->{}: {}", iter, index, amp_index, output[0]); + *amplifiers[index].2 = result.instruction; + *amplifiers[index].3 = result.status; + } + iter += 1; + } +} + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn example_1() { + let program = vec![3,15,3,16,1002,16,10,16,1,16,15,15,4,15,99,0,0]; + let settings = vec![4, 3, 2, 1, 0]; + assert_eq!(run_amplifiers(&program, settings), 43210); + } + + #[test] + fn example_2() { + let program = vec![3,23,3,24,1002,24,10,24,1002,23,-1,23,101,5,23,23,1,24,23,23,4,23,99,0,0]; + let settings = vec![0,1,2,3,4]; + assert_eq!(run_amplifiers(&program, settings), 54321); + } + + #[test] + fn example_3() { + let program = vec![3,31,3,32,1002,32,10,32,1001,31,-2,31,1007,31,0,33,1002,33,7,33,1,33,31,31,1,32,31,31,4,31,99,0,0,0]; + let settings = vec![1,0,4,3,2]; + assert_eq!(run_amplifiers(&program, settings), 65210); + } + + #[test] + fn part2_example_1() { + let program = vec![3,26,1001,26,-4,26,3,27,1002,27,2,27,1,27,26,27,4,27,1001,28,-1,28,1005,28,6,99,0,0,5]; + let settings = vec![9,8,7,6,5]; + assert_eq!(run_feedback_amplifiers(&program, settings), 139629729); + } + + #[test] + fn part2_example_2() { + let program = vec![3,52,1001,52,-5,52,3,53,1,52,56,54,1007,54,5,55,1005,55,26,1001,54,-5,54,1105,1,12,1,53,54,53,1008,54,0,55,1001,55,1,55,2,53,55,53,4,53,1001,56,-1,56,1005,56,6,99,0,0,0,0,10]; + let settings = vec![9,7,8,5,6]; + assert_eq!(run_feedback_amplifiers(&program, settings), 18216); + } +} diff --git a/day8/Cargo.lock b/day8/Cargo.lock new file mode 100644 index 0000000..0a523ad --- /dev/null +++ b/day8/Cargo.lock @@ -0,0 +1,7 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "day8" +version = "0.1.0" diff --git a/day8/Cargo.toml b/day8/Cargo.toml new file mode 100644 index 0000000..4879259 --- /dev/null +++ b/day8/Cargo.toml @@ -0,0 +1,8 @@ +[package] +name = "day8" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] diff --git a/day8/input b/day8/input new file mode 100644 index 0000000..35bfb34 --- /dev/null +++ b/day8/input @@ -0,0 +1 @@ +222222222022202221221222200020120222202020222120222201212202122222222212222222222222222202222222222222212222222222222212222222222222202222222222212222222222222122202222222222211121122222202020222220222200222202222222222222222222222222222202222222222222212222222222222212222222222222212222222222212222222222222022222222221222201020022222212020222121222222202222022222222202222022222222222222222222222222202222222222222212222222222222202222122222202222222222222122212220220222212021120222202222222220222210222202222222222202222222222222222202222222222222202222222222222222222222222222212222120222212222222222222122202222222222222121021222212121222022222211202222122222222222222122222222222202222222222222202222222222222202222222222222222222221222222222222222222222202220222222210121222222222122222221222220212212022222222212222122222222222202222222222222202222222222222202222222222222202222020222222222202222222022212222221222210221021222202222222021222201202202122222222202222122222222222212222222222222222222222222222222222222222222202222121222202222222222222122212221222222211220221222212220222020222221222212022222222222222222222222222222222222222222222222222222222202222222222222222222222222222222202222222222202222221222210121020222202122222121222212202222122222222222222222222222222202222222222222202222222222222222222222222222202222020220202222202222222022222221222222200022222222222022222121222201222222022222222212222122222222222212222222222222212222222222222222222222222222202222222221202222212222222122202220222222200121121222222120222122222221212212122222222212222122222222222202222222222222212222222222222222222222222222202222022220202222222222222022202220221222222121221222222020222020222200202202222222222202222122222222222202222222222222202222222222222202222222222222202222220222212222222222222222222222221222221021222222222021222021222222212202022222222222222122222222222202222222222222212222222222222212222222222222212222122220212222202222222022222222222222212220022222202021222222222200222212022222222202222122222222222202222222222222222222222222222212222222222222202222220222202222202222222122212221222222221022121222222121222122222222212222222222222222222222222222222222222222222222222222222222222222222222222222222202020221222222202222222022222222220222211220222222202121222120222200210212222222222222222222202222222212222222222222212222222222222212222222222222222212220222212222222222222222222220220222010122221222202222222122222202221202122222222222222122202222222212222222222220222222222222222222222222222222202202022222212222202222222122222220202212002120021222212222222122222222201202222222222202222222212222222222222222222220212222222222222202222222222222212222002220202222212222222122222222201202122121122222212020222020222210211222022222222202222222212222222222222222222220202222222222222212222222222222202212121221222222202222222122222220221202010022022222222020022122222200222222122222222212222022222222222202222222222222212222222022222202222222222222212222222221222222202222222022222222200222212022120222222221222220222210201202102222222202222222212222222212222222222222202222222022222222222222222222202212102220212222212222222122212221221212020220022222202221222021222210211222122222222202222122222222222202222222222222212222222122222202222222222222222212010221222222222222222022222220202212021121222222222221222122222221201222102222222212222222212222222222222222222221202222222122222222222222222222222202120222222222222222222222222221200212121021222222222212122120222201200212112222222222222122202222222222222222222220222222222122222212222222222222220222010220202222202222222022222222201222111221022222202102022221222201211222102222222202222122222222222212222222222220222222222222222222222222222222210212212220222222212222222022202222201202022221120222212102222221222201212202112222222212222022202222222212222222222222202222222022222212222222222222221212212221222222212222222022222222211222201120021222222011122021222210220212212222222222222122222222222202222222222220222222222122222212222222222222200212120220202222212222222122212220211222111121021222222010022220222210201222122222222222222222202222222222222222222221202222122222222202222222222222221222210222212222202222222022202222220202220221220222212000022121222202201222212222222202222122202222222222222222222220222222222222222202222222222222202222101222221222202222222022222221201222110021120222222202022220222222210202012222222212222122212222222212222222222222202220122122222212222222222222211212120222022222212222222222212221202212012021021222212201122222222202211222122222222212222022202222222212222222222221202222002022222202122222222222222222102220000222222222222222212220210222010220121222202011022221222222202222222222222222222222202222222212222222222220222221012122222222102222222222201212122221102222202222222122202221221222200022220222202221022120222210210212002202222222222122222222222212222222222222222221102022222222202222222222221222200221020222212222222222222222201202201022020222202021122221222202202222122222222212222022212222222212222222202221212222112122222212002222222222220202221220201222202222222122202222222212102120022222222100022122222200210222112212202222222122202222222222222222212221212220012022222202112222222222212202220220202222202222222222212221200222110122121222212022122221222210202222002202212202222122212222222222222222211221212220122222222222222222222222220202012221012222202222222022222221221222000021222222222012122020222211222222212212202202222122212222222212222222220220212221222122222212012222222222202202010221121222222222222022202220221222021211222222222210222220202220221222112212202212222022222222222222222222221222212220222022222202202222222222221222002221202222212202222222222221221202200202120222222100222121200220220212022222202222222022212222222222222222222020222220222222222202202222222222211222211222202222222202222122202220211222221112221222222022012022222220220202102202212202222022222222222202222222202220222221222022222202122222222222222202100222020222202222222222202221200222101002220222212211012020220221201202222222222212222022222222222222222222201121202220202222222202212222222222222212002220012222212212222022202221200212210020021222222100202221220221210202022212202202222222222202222222222222221120212221202222222202012222222222212212111220200222202212222122212221202222221120020222212101222120220201222212212212212202222222212202222222222222210122222222022122222202112222222222200202111221010222202212222122222222210202122010220222202120212222212202202222102212202222222122212212222200122222210222222222122222222222122222222222202222212221022222222202222222212222211212020110221222222221222221202211201212222202202202222122222202222222222222201221202221022122222202002222222222200212011220101222202222222122222222202212011012120222212220102021211211211002222222212212222022212212022221122222200220222222022022222212102222222222201202110220001222212212222122212220202212212201222222222121222221201210220102222202222222222022202202022221022222222220202222122122222212012222222222202202001221001222202212222022222220221212001100021222202022112220202222211102012212212002222222202212022212122222201220222220122122222212012222222222220222112222122222222202222122220221220222101010121222212210022120221211202022002212212212222022222212222222022222220021212222112222222222022222222222200202120220221222212202222222220221211212100101121222202111002220202202221002222212202022222122202212122211222222200222222220012122222222022222222222222222122221012222212212222222201222222222202101020222222001212021220212201112222202202202222022222222122202122222221122212221112222222212212222222222202222020210011222222212222222201221210202200220121201222201222121220201201022122212222002222222202212022221022222201220202221002022222202202222222222221222011221200222212212220222200220221222002001221211222122012222201202222002112222212212222022202222022211022222200222212220022112222202012222222222211202001201001222222222221222211221202212201111022212202002112022201202211222012212202002222122212202222201122222200121202222212012222202212220222222211202022210120222202202220222201221220202101122021201212120222222221200221122012212222012222222222222222221222222211220222222222212222222012221122202201212120212211222212222222122200222212222202110222211212020022122210220202002112202222002222022212202222202122222200120212222202122222212112221022212200202210201221222212222120122212220222222020101222212222201222021200210212202202212212102222022202212222221222222201022222220212122222212002222222202201212020220012222202222220222212221211202121020221202212120012221222210212102222222202012222022212222022211022222212021222221102212222222222222222202211212101200100222202222121222220220220202100101020212212221102121212222200102212222202122222222222222122102222222202122202220002022222220212222222212211212221201200222202202122222200221201202120102120221212101222120212200212012022222212012222222222202022010222222200022222222002202222200122221122202212222001222122222222212221122221220202202001022021200212012010222201221201012012212202022222222212212222002022222222221202220222222222220202221022212221202012212000222222212220122211221222202121000222211202111012120201220202212102202212002222222202212222022122222210022212221202102222211222220022212211222010220102222212222021222211220222222220021220201202122201122200202220222122202202012222122212202222000222222212222212221212022222202022121122222201202122220112222202202020122210220220212012121021212202200212122211211221112102202210122222122222202022021222222202021202221012102222211112221222202220222111210000222212202021122201221212222012221120212212001211021201211200012122202212002222022202222222220122222202020222222012022222222202020222202221202002200122222202212220122222220220202012100220221202001102221222212222202012222201222222122212222022221122222202020222222202102222222022222122202201202110222010222202222021122221220201222120012020222222200221221200221212002222222202102222022212202122002122022201022222222022122222220122120022222202202112222100222222222120122222221221112222202221222212010002222200202200002222212002112222222202212022222122022222220212220222202222221202221222222200212020220000222222212120222221220212002110222120212212000010022222221222222102202022222222022222202222121022222210122202220102202222211202121022212221202112211110222212212021022220222010222010001021211212022022122210201221102222222021102222222212202122210122102222220202222002022222210022020122222222212210201101222222222122222221220001012110121120200001121220022221212202002212222102202122022222212222110222102211222222221202202222220222121122212202212010200101220202212120222202222121012022001021211000222011020212201222002002222000102222122222202022220222212200022222221002002222202202220122202212222000222102221212212221122201220212002200021121211211021100020211220222202212222101022022022222212222220222202201211212220202202222201002020122222212222111202002220212222020212212222002022120221122211200102001120221201200012222222201002222222211222222210122112220022222202122102222201022021222212211212122202211220222222122002220221220012021001221201001102101022202202220022222212111011022222201222122202122222222200202202022122222202102121222202221202112211110222222222020222202221102122120221122221010112211121210201011122122202212112222122201202022010022112202012222201102112222212122020222222222202111202120222202202122102211222211012100121022220200210000121212200011102202202120011222222200222022220022222211102222220122202222200212220022222210212000210111220222212120122212220101212010102020200210002120122222222001022002212202102222022220222222101022002212111202211202002222212212122022202221202110201200222212212120012201222122202212011020212012222100221212202001112022212100212222122112222022102022222220211210201222202222200202021022002210222201201012222222212021122201221201102100001121200210222010020210211210002012222121002122122001202112100122122202111222210212202222212002221022122212212012211212221212212121022211222222102011000122121001202212022212212222022122202102202002222220212122022022022202020210211022002222222122021022012210222012202111222212212022102220222221112001012122111022022110220212220021002012212111211122022200222002211222012010211201211002002222221222121122102221222101210002221222222120102212220101102220200122022220000212222221212211222122222222001212220000212002021222202121212201222212222222211112021222112202222200221220222202202020022210221210102122211222122021112000121210212000012122202122001012220121022002121222012122000201221012212222210002021122222222212201222121222202202220102201222102212020211221011202011222221212210221102112212122002012121101102102102022112001221220220122222220212212121222002221202110201020221212202022102220222202002210211221220201200122221222211201122002122200211122120122002002020022212012211220210022222222220002020022102212222101220120222212212221112221222002212222012222000010211021020220222111122222022112121012221201112222200022012120020220202102122221200002022122112211202020211201220222222120012212221102222212221221022101200002022211220201112122222112120102222102002212002222112201220201221212220221201102221122102201222112210020220212222120012102220211022012002120000211110000022211220112002222222210220002121222102002120222102002110202211012210221220102220122222200212020200021220202222120212202222000222121211221210210121000021211212101102212112201011002121211112112222222002000201202222102010210200022000022012220222200222020222212222121002001222121212101000021212012202212020222211102022202022012010012222021110112200222021111000220200022000201201102121122102200202001222220222012212222212121220011112111022221210200111011022200220100012002112101012112021210011122220022102022212222200202110222221112001222012211212220200121220112212020212012220221112111200001102002201122220200222002112202002202011012022020211202002222120122022210211122201210222102001122002222102122220222220012212122022000221212012011222221000202102010220221221222022012102122111202222112222212111122102022222201220122120202220112002122202221222000221102201012212121112110222111022100102120101201020202221201222022102222122102012112220002001222120122222022211221210002121202202222202222122222102012212012210102202220112112020001122011002100000200122200221222222121220222202002221002021121001222210222100110022200220222121221211112212122012201222202221101200202202222212100022012212212222200120110210121022101200210021102112022012122221120020112220222000020020210212202021222221112120022112201122210212020202112202120122010020201112101222220000120002002022210210022220012112200011212221201012002222122211020101212211222121220221202021222202222112121222220212202212121212201022110212110111110010102220112221101212202102212222211201102022112022011011222210221002210201112020222201012121022112100022120222121220211120211001120210211020102000200102112021201102012000220121010201212122010202001110200012200100022020022110111220010011010002010011201000010122212121 \ No newline at end of file diff --git a/day8/src/main.rs b/day8/src/main.rs new file mode 100644 index 0000000..d73068b --- /dev/null +++ b/day8/src/main.rs @@ -0,0 +1,122 @@ +struct Image { + width: usize, + height: usize, + layers: Vec>, +} + +impl Image { + fn from_str(width: usize, height: usize, data: &str) -> Image { + assert_eq!(data.len() % (width * height), 0); + let mut image = Image { + width: width, + height: height, + layers: Vec::new(), + }; + let mut layer: usize = 0; + image.layers.push(Vec::new()); + let mut index: usize = 0; + for c in data.chars() { + if index >= (width*height) { + layer += 1; + image.layers.push(Vec::new()); + index = 0; + } + image.layers[layer].push(c.to_digit(10).expect("Could not convert character to digit")); + index += 1; + } + return image; + } + + fn layer_n_digits(&self, layer_index: usize, value: u32) -> usize { + let mut count: usize = 0; + for v in self.layers[layer_index].iter() { + if *v == value { + count += 1; + } + } + return count; + } + + fn layer_merge(&self) -> Vec { + let mut result: Vec = Vec::new(); + result.resize(self.width * self.height, 2); + for pixel_index in 0..(self.width*self.height) { + for layer_index in 0..self.layers.len() { + // 2 is transparent + let value = self.layers[layer_index][pixel_index]; + if value != 2 { + result[pixel_index] = value; + break; + } + } + } + return result; + } +} + +fn main() { + let data = std::fs::read_to_string("input") + .expect("Failed to read 'input'"); + let image = Image::from_str(25, 6, &data); + println!("Image contains {} layers", image.layers.len()); + let mut layer_fewest_zeroes: usize = 0; + let mut least_zeroes: usize = 200; + for index in 0..image.layers.len() { + let n_zeroes = image.layer_n_digits(index, 0); + if n_zeroes < least_zeroes { + layer_fewest_zeroes = index; + least_zeroes = n_zeroes; + } + } + println!("Layer {} has {} zeroes", layer_fewest_zeroes, least_zeroes); + println!("[Part 1] {}", image.layer_n_digits(layer_fewest_zeroes, 1) * image.layer_n_digits(layer_fewest_zeroes, 2)); + + let merged = image.layer_merge(); + let mut n: u32 = 0; + for i in merged.iter() { + let c = if *i == 0 { + '⬛' + } else if *i == 1 { + '⬜' + } + else if *i == 2 { + ' ' + } + else { + '?' + }; + print!("{}", c); + n += 1; + if n % 25 == 0 { + print!("\n"); + } + } +} + +#[cfg(test)] +mod test { + + use super::*; + + #[test] + fn create_image() { + let data = "123456789012"; + let image = Image::from_str(3, 2, data); + assert_eq!(image.layers.len(), 2); + let layer_0 = vec![1, 2, 3, 4, 5, 6]; + let layer_1 = vec![7, 8, 9, 0, 1, 2]; + assert_eq!(image.layers[0], layer_0); + assert_eq!(image.layers[1], layer_1); + } + + #[test] + fn layer_merge() { + let data = "0222112222120000"; + let image = Image::from_str(2, 2, data); + let merged = image.layer_merge(); + assert_eq!(merged[0], 0); + assert_eq!(merged[1], 1); + assert_eq!(merged[2], 1); + assert_eq!(merged[3], 0); + } +} diff --git a/day9/Cargo.lock b/day9/Cargo.lock new file mode 100644 index 0000000..1047ada --- /dev/null +++ b/day9/Cargo.lock @@ -0,0 +1,14 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "day9" +version = "0.1.0" +dependencies = [ + "icc", +] + +[[package]] +name = "icc" +version = "1.1.2" diff --git a/day9/Cargo.toml b/day9/Cargo.toml new file mode 100644 index 0000000..91703e2 --- /dev/null +++ b/day9/Cargo.toml @@ -0,0 +1,9 @@ +[package] +name = "day9" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +icc = { path = "../icc", version = "1.1.1"} diff --git a/day9/input b/day9/input new file mode 100644 index 0000000..f8328c5 --- /dev/null +++ b/day9/input @@ -0,0 +1 @@ +1102,34463338,34463338,63,1007,63,34463338,63,1005,63,53,1101,0,3,1000,109,988,209,12,9,1000,209,6,209,3,203,0,1008,1000,1,63,1005,63,65,1008,1000,2,63,1005,63,904,1008,1000,0,63,1005,63,58,4,25,104,0,99,4,0,104,0,99,4,17,104,0,99,0,0,1102,1,432,1027,1101,439,0,1026,1101,0,36,1010,1101,0,34,1018,1102,278,1,1029,1101,0,24,1002,1102,1,20,1016,1102,1,31,1011,1102,319,1,1024,1102,21,1,1012,1102,1,763,1022,1102,1,25,1007,1101,0,287,1028,1102,32,1,1008,1101,0,22,1013,1102,38,1,1001,1101,0,314,1025,1102,35,1,1009,1102,1,23,1015,1102,39,1,1019,1102,27,1,1000,1102,1,37,1003,1102,1,28,1017,1101,0,0,1020,1101,0,29,1004,1102,1,30,1006,1102,1,756,1023,1102,1,33,1005,1101,0,1,1021,1102,26,1,1014,109,13,2108,28,-7,63,1005,63,201,1001,64,1,64,1105,1,203,4,187,1002,64,2,64,109,8,21107,40,41,-3,1005,1018,225,4,209,1001,64,1,64,1105,1,225,1002,64,2,64,109,-3,1206,2,239,4,231,1105,1,243,1001,64,1,64,1002,64,2,64,109,-21,1201,6,0,63,1008,63,35,63,1005,63,267,1001,64,1,64,1105,1,269,4,249,1002,64,2,64,109,35,2106,0,-4,4,275,1001,64,1,64,1105,1,287,1002,64,2,64,109,-11,1205,-1,303,1001,64,1,64,1105,1,305,4,293,1002,64,2,64,109,8,2105,1,-5,4,311,1106,0,323,1001,64,1,64,1002,64,2,64,109,-7,21108,41,38,-6,1005,1016,339,1106,0,345,4,329,1001,64,1,64,1002,64,2,64,109,2,21102,42,1,-8,1008,1016,45,63,1005,63,369,1001,64,1,64,1105,1,371,4,351,1002,64,2,64,109,-14,21101,43,0,1,1008,1011,43,63,1005,63,397,4,377,1001,64,1,64,1106,0,397,1002,64,2,64,109,-8,21101,44,0,8,1008,1010,47,63,1005,63,417,1105,1,423,4,403,1001,64,1,64,1002,64,2,64,109,25,2106,0,0,1001,64,1,64,1105,1,441,4,429,1002,64,2,64,109,-20,2107,37,-6,63,1005,63,463,4,447,1001,64,1,64,1106,0,463,1002,64,2,64,109,8,2108,25,-8,63,1005,63,485,4,469,1001,64,1,64,1106,0,485,1002,64,2,64,109,-1,21107,45,44,-1,1005,1013,505,1001,64,1,64,1106,0,507,4,491,1002,64,2,64,109,-11,1207,-1,25,63,1005,63,529,4,513,1001,64,1,64,1106,0,529,1002,64,2,64,109,23,1206,-5,545,1001,64,1,64,1106,0,547,4,535,1002,64,2,64,109,-31,2102,1,5,63,1008,63,27,63,1005,63,569,4,553,1106,0,573,1001,64,1,64,1002,64,2,64,109,27,21102,46,1,-9,1008,1013,46,63,1005,63,595,4,579,1105,1,599,1001,64,1,64,1002,64,2,64,109,-26,2101,0,6,63,1008,63,24,63,1005,63,625,4,605,1001,64,1,64,1106,0,625,1002,64,2,64,109,5,1208,0,37,63,1005,63,645,1001,64,1,64,1105,1,647,4,631,1002,64,2,64,109,7,2102,1,-3,63,1008,63,31,63,1005,63,671,1001,64,1,64,1105,1,673,4,653,1002,64,2,64,109,2,1202,-5,1,63,1008,63,33,63,1005,63,699,4,679,1001,64,1,64,1105,1,699,1002,64,2,64,109,-4,2101,0,-3,63,1008,63,35,63,1005,63,719,1105,1,725,4,705,1001,64,1,64,1002,64,2,64,109,-5,1207,4,32,63,1005,63,741,1106,0,747,4,731,1001,64,1,64,1002,64,2,64,109,29,2105,1,-7,1001,64,1,64,1106,0,765,4,753,1002,64,2,64,109,-26,2107,36,5,63,1005,63,781,1105,1,787,4,771,1001,64,1,64,1002,64,2,64,109,10,1201,-6,0,63,1008,63,32,63,1005,63,809,4,793,1106,0,813,1001,64,1,64,1002,64,2,64,109,3,21108,47,47,-5,1005,1012,835,4,819,1001,64,1,64,1106,0,835,1002,64,2,64,109,-24,1202,9,1,63,1008,63,25,63,1005,63,859,1001,64,1,64,1106,0,861,4,841,1002,64,2,64,109,19,1205,9,875,4,867,1106,0,879,1001,64,1,64,1002,64,2,64,109,-3,1208,-1,32,63,1005,63,897,4,885,1106,0,901,1001,64,1,64,4,64,99,21102,27,1,1,21101,915,0,0,1105,1,922,21201,1,60043,1,204,1,99,109,3,1207,-2,3,63,1005,63,964,21201,-2,-1,1,21102,1,942,0,1106,0,922,21202,1,1,-1,21201,-2,-3,1,21101,957,0,0,1106,0,922,22201,1,-1,-2,1105,1,968,22102,1,-2,-2,109,-3,2105,1,0 \ No newline at end of file diff --git a/day9/src/main.rs b/day9/src/main.rs new file mode 100644 index 0000000..c3384c5 --- /dev/null +++ b/day9/src/main.rs @@ -0,0 +1,26 @@ +use std::str::FromStr; + +fn main() { + let data = std::fs::read_to_string("input") + .expect("Failed to read 'input'"); + let mut program: Vec = Vec::new(); + for v in data.split(",") { + program.push(i64::from_str(v).unwrap()); + } + + { + let mut c = icc::Computer::initialize(program.clone(), vec![1]); + c.run(); + if c.output.len() > 1 { + println!("Some op-codes report failures"); + println!("Test output: {:?}", c.output); + return; + } + println!("[Part 1] {}", c.output[0]); + } + { + let mut c = icc::Computer::initialize(program.clone(), vec![2]); + c.run(); + println!("[Part 2] {}", c.output[0]); + } +} diff --git a/icc/Cargo.lock b/icc/Cargo.lock new file mode 100644 index 0000000..2190e97 --- /dev/null +++ b/icc/Cargo.lock @@ -0,0 +1,7 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "icc" +version = "1.1.2" diff --git a/icc/Cargo.toml b/icc/Cargo.toml new file mode 100644 index 0000000..45ae7db --- /dev/null +++ b/icc/Cargo.toml @@ -0,0 +1,8 @@ +[package] +name = "icc" +version = "1.1.2" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] diff --git a/icc/src/lib.rs b/icc/src/lib.rs new file mode 100644 index 0000000..cbb3a34 --- /dev/null +++ b/icc/src/lib.rs @@ -0,0 +1,500 @@ +use std::collections::VecDeque; +use std::collections::HashMap; + +#[derive(Debug)] +#[derive(PartialEq)] +#[derive(Copy, Clone)] +pub enum Status { + Running, + Finished, + WaitingForInput, +} + +pub struct Result { + pub status: Status, + pub instruction: usize, +} + +pub struct Computer { + memory: HashMap, + position: usize, + relative_base: i64, + input: VecDeque, + pub output: Vec, +} + +#[derive(Debug)] +#[derive(Copy, Clone)] +enum Operation { + Add, + Mul, + Input, + Output, + JumpIfTrue, + JumpIfFalse, + LessThan, + Equals, + AdjustRelativeBase, + End, // 99 +} + +#[derive(Debug)] +#[derive(Copy, Clone)] +enum ParameterMode { + Position, // 0 + Immediate, // 1 + Relative, // 2 +} + +impl ParameterMode { + pub fn from_int(i: i64) -> ParameterMode { + if i == 0 { + ParameterMode::Position + } + else if i == 1 { + ParameterMode::Immediate + } + else if i == 2 { + ParameterMode::Relative + } + else { + panic!("Unknown parameter mode integer value: {}", i); + } + } +} + +impl Computer { + pub fn initialize(program: Vec, input: Vec) -> Self { + let mut computer = Computer { + memory: HashMap::new(), + position: 0, + relative_base: 0, + input: VecDeque::from(input), + output: Vec::new(), + }; + for i in 0..program.len() { + computer.mem_put(i, program[i]); + } + return computer; + } + + fn mem_put(&mut self, address: usize, value: i64) { + self.memory.insert(address, value); + } + + fn mem_get(&mut self, address: usize) -> i64 { + let value = self.memory.get(&address); + if value.is_none() { + self.mem_put(address, 0); + return 0; + } + return *value.unwrap(); + } + + pub fn run(&mut self) -> Status { + loop { + let (op, p1_mode, p2_mode, p3_mode) = Self::decode_instruction( + self.mem_get(self.position) + ); + match op { + Operation::Add => { + let d1 = self.fetch(self.position + 1, p1_mode); + let d2 = self.fetch(self.position + 2, p2_mode); + let dest = self.absolute_address(self.position + 3, p3_mode); + self.mem_put(dest, d1 + d2); + self.position += 4; + }, + Operation::Mul => { + let d1 = self.fetch(self.position + 1, p1_mode); + let d2 = self.fetch(self.position + 2, p2_mode); + let dest = self.absolute_address(self.position + 3, p3_mode); + self.mem_put(dest, d1 * d2); + self.position += 4; + }, + Operation::Input => { + if self.input.len() == 0 { + return Status::WaitingForInput; + } + let dest = self.absolute_address(self.position + 1, p1_mode); + let input = self.input.pop_front().expect("Input queue empty... weird"); + self.mem_put(dest, input); + println!("Input: {}", input); + self.position += 2; + }, + Operation::Output => { + let value = self.fetch(self.position + 1, p1_mode); + println!("Output: {}", value); + self.output.push(value); + self.position += 2; + }, + Operation::JumpIfTrue => { + let d1 = self.fetch(self.position + 1, p1_mode); + let d2 = self.fetch(self.position + 2, p2_mode); + if d1 != 0 { + self.position = d2 as usize; + } + else { + self.position += 3; + } + }, + Operation::JumpIfFalse => { + let d1 = self.fetch(self.position + 1, p1_mode); + let d2 = self.fetch(self.position + 2, p2_mode); + if d1 == 0 { + self.position = d2 as usize; + } + else { + self.position += 3; + } + }, + Operation::LessThan => { + let d1 = self.fetch(self.position + 1, p1_mode); + let d2 = self.fetch(self.position + 2, p2_mode); + let dest = self.absolute_address(self.position + 3, p3_mode); + self.mem_put(dest, if d1 < d2 { 1 } else { 0 }); + self.position += 4; + }, + Operation::Equals => { + let d1 = self.fetch(self.position + 1, p1_mode); + let d2 = self.fetch(self.position + 2, p2_mode); + let dest = self.absolute_address(self.position + 3, p3_mode); + self.mem_put(dest, if d1 == d2 { 1 } else { 0 }); + self.position += 4; + }, + Operation::AdjustRelativeBase => { + self.relative_base += self.fetch(self.position + 1, p1_mode); + //println!("[RB: {}]", self.relative_base); + self.position += 2; + }, + Operation::End => { + break; + }, + other => { + panic!("'{:?}' not implemented", other); + }, + }; + } + return Status::Finished; + } + + fn fetch(&mut self, pos: usize, mode: ParameterMode) -> i64 { + let addr = self.absolute_address(pos, mode); + return self.mem_get(addr); + } + + fn absolute_address(&mut self, pos: usize, mode: ParameterMode) -> usize { + match mode { + ParameterMode::Position => { + self.mem_get( + pos + ) as usize + }, + ParameterMode::Immediate => { + pos + }, + ParameterMode::Relative => { + let p = self.mem_get(pos) as i64 + self.relative_base; + if p < 0 { + panic!("Attempting to resolve illegale address: {}", p); + } + return p as usize; + } + } + } + + fn decode_instruction(code: i64) -> (Operation, ParameterMode, ParameterMode, ParameterMode) { + // Opcodes are ABCDE, where the op is DE + // the modes for params 1, 2, and 3 as C, B, A + // respectively. + let mut c = code; + let op_int = code % 100; + let op = if op_int == 1 { + Operation::Add + } else if op_int == 2 { + Operation::Mul + } else if op_int == 3 { + Operation::Input + } else if op_int == 4 { + Operation::Output + } else if op_int == 5 { + Operation::JumpIfTrue + } else if op_int == 6 { + Operation::JumpIfFalse + } else if op_int == 7 { + Operation::LessThan + } else if op_int == 8 { + Operation::Equals + } else if op_int == 9 { + Operation::AdjustRelativeBase + }else if op_int == 99 { + Operation::End + } else { + panic!("Unknown opcode: {}", op_int); + }; + + let param_3_mode_int = c / 10000; + c -= param_3_mode_int * 10000; + let param_2_mode_int = c / 1000; + c -= param_2_mode_int * 1000; + let param_1_mode_int = c / 100; + return ( + op, + ParameterMode::from_int(param_1_mode_int), + ParameterMode::from_int(param_2_mode_int), + ParameterMode::from_int(param_3_mode_int), + ); + } +} + +pub fn simulate(v: &mut Vec, input: &mut VecDeque, output: &mut Vec, start: usize) -> Result { + let mut program: Vec = Vec::new(); + for i in 0..v.len() { + program.push(i64::from(v[i])); + } + let mut ip: VecDeque = VecDeque::new(); + for i in 0..input.len() { + ip.push_front(i64::from(input[i])); + } + let mut computer = Computer::initialize(program, vec![]); + computer.input = ip; + computer.position = start; + let r = computer.run(); + for i in 0..computer.output.len() { + if computer.output[i] <= i64::from(i32::MAX) && computer.output[i] >= i64::from(i32::MIN) { + output.push(computer.output[i] as i32); + } + else { + panic!("Output value '{}' out of range for legacy i32 int-code computer", computer.output[i]); + } + } + for i in 0..v.len() { + v[i] = computer.mem_get(i) as i32; + } + return Result { + status: r, + instruction: computer.position, + }; +} + +#[cfg(test)] +mod tests { + use super::*; + #[test] + fn test_op_1() { + let mut program = vec![1, 0, 0, 0, 99]; + let mut input: VecDeque = VecDeque::new(); + let mut output: Vec = Vec::new(); + simulate(&mut program, &mut input, &mut output, 0); + assert_eq!(program[0], 2); + } + + #[test] + fn test_op_2() { + let mut program = vec![2, 3, 0, 3, 99]; + let mut input: VecDeque = VecDeque::new(); + let mut output: Vec = Vec::new(); + simulate(&mut program, &mut input, &mut output, 0); + assert_eq!(program[3], 6); + } + + #[test] + fn test_case_3() { + let mut program = vec![2,4,4,5,99,0]; + let mut input: VecDeque = VecDeque::new(); + let mut output: Vec = Vec::new(); + simulate(&mut program, &mut input, &mut output, 0); + assert_eq!(program[program.len() - 1], 9801); + } + + #[test] + fn test_case_4() { + let mut program = vec![1,1,1,4,99,5,6,0,99]; + let mut input: VecDeque = VecDeque::new(); + let mut output: Vec = Vec::new(); + simulate(&mut program, &mut input, &mut output, 0); + assert_eq!(program[0], 30); + assert_eq!(program[4], 2); + } + + #[test] + fn immediate_mode_multiply() { + let mut program = vec![1002,4,3,4,33]; + let mut input: VecDeque = VecDeque::new(); + let mut output: Vec = Vec::new(); + simulate(&mut program, &mut input, &mut output, 0); + assert_eq!(program[4], 99); + } + + #[test] + fn negative_integers() { + let mut program = vec![1101,100,-1,4,0]; + let mut input: VecDeque = VecDeque::new(); + let mut output: Vec = Vec::new(); + simulate(&mut program, &mut input, &mut output, 0); + assert_eq!(program[4], 99); + } + + #[test] + fn position_mode_input_equal_to_8() { + let mut program = vec![3,9,8,9,10,9,4,9,99,-1,8]; + let mut output: Vec = Vec::new(); + let backup = program.clone(); + simulate(&mut program, &mut VecDeque::from([8]), &mut output, 0); + assert_eq!(output[0], 1); + output.clear(); + program = backup.clone(); + simulate(&mut program, &mut VecDeque::from([7]), &mut output, 0); + assert_eq!(output[0], 0); + } + + #[test] + fn position_mode_input_less_than_8() { + let mut program = vec![3,9,7,9,10,9,4,9,99,-1,8]; + let mut output: Vec = Vec::new(); + let backup = program.clone(); + simulate(&mut program, &mut VecDeque::from([8]), &mut output, 0); + assert_eq!(output[0], 0); + output.clear(); + program = backup.clone(); + simulate(&mut program, &mut VecDeque::from([7]), &mut output, 0); + assert_eq!(output[0], 1); + } + + #[test] + fn immediate_mode_input_equal_to_8() { + let mut program = vec![3,3,1108,-1,8,3,4,3,99]; + let mut output: Vec = Vec::new(); + let backup = program.clone(); + simulate(&mut program, &mut VecDeque::from([8]), &mut output, 0); + assert_eq!(output[0], 1); + output.clear(); + program = backup.clone(); + simulate(&mut program, &mut VecDeque::from([7]), &mut output, 0); + assert_eq!(output[0], 0); + } + + #[test] + fn immediate_mode_input_less_than_8() { + let mut program = vec![3,3,1107,-1,8,3,4,3,99]; + let mut output: Vec = Vec::new(); + let backup = program.clone(); + simulate(&mut program, &mut VecDeque::from([8]), &mut output, 0); + assert_eq!(output[0], 0); + output.clear(); + program = backup.clone(); + simulate(&mut program, &mut VecDeque::from([7]), &mut output, 0); + assert_eq!(output[0], 1); + } + + #[test] + fn position_mode_input_is_non_zero() { + let mut program = vec![3,12,6,12,15,1,13,14,13,4,13,99,-1,0,1,9]; + let mut output: Vec = Vec::new(); + let backup = program.clone(); + simulate(&mut program, &mut VecDeque::from([8]), &mut output, 0); + assert_eq!(output[0], 1); + output.clear(); + program = backup.clone(); + simulate(&mut program, &mut VecDeque::from([0]), &mut output, 0); + assert_eq!(output[0], 0); + } + + #[test] + fn immediate_mode_input_is_non_zero() { + let mut program = vec![3,3,1105,-1,9,1101,0,0,12,4,12,99,1]; + let mut output: Vec = Vec::new(); + let backup = program.clone(); + simulate(&mut program, &mut VecDeque::from([9]), &mut output, 0); + assert_eq!(output[0], 1); + output.clear(); + program = backup.clone(); + simulate(&mut program, &mut VecDeque::from([0]), &mut output, 0); + assert_eq!(output[0], 0); + } + + #[test] + fn multi_jump() { + let mut program = vec![3,21,1008,21,8,20,1005,20,22,107,8,21,20,1006,20,31,1106,0,36,98,0,0,1002,21,125,20,4,20,1105,1,46,104,999,1105,1,46,1101,1000,1,20,4,20,1105,1,46,98,99]; + let mut output: Vec = Vec::new(); + let backup = program.clone(); + simulate(&mut program, &mut VecDeque::from([7]), &mut output, 0); + assert_eq!(output[0], 999); + output.clear(); + program = backup.clone(); + simulate(&mut program, &mut VecDeque::from([8]), &mut output, 0); + assert_eq!(output[0], 1000); + output.clear(); + program = backup.clone(); + simulate(&mut program, &mut VecDeque::from([9]), &mut output, 0); + assert_eq!(output[0], 1001); + } + + #[test] + fn blocks_on_input() { + let mut program = vec![3,26,1001,26,-4,26,3,27,1002,27,2,27,1,27,26,27,4,27,1001,28,-1,28,1005,28,6,99,0,0,5]; + let mut output: Vec = Vec::new(); + let result = simulate(&mut program, &mut VecDeque::from([9, 0]), &mut output, 0); + assert_eq!(result.status, Status::WaitingForInput); + assert_eq!(result.instruction, 6); + } + + #[test] + fn relative_base_adjust() { + let mut c = Computer::initialize(vec![109, 1, 99], vec![]); + c.run(); + assert_eq!(c.relative_base, 1); + } + + #[test] + #[should_panic] + fn negative_memory_access() { + let mut c = Computer::initialize(vec![109, -5000, 204, 0, 99], vec![]); + c.run(); + } + + #[test] + fn relative_example_1() { + // The program produces an output of itself + let program = vec![109,1,204,-1,1001,100,1,100,1008,100,16,101,1006,101,0,99]; + let mut c = Computer::initialize(program.clone(), vec![]); + c.run(); + for i in 0..program.len() { + assert_eq!(program[i], c.output[i]); + } + } + + #[test] + fn relative_example_2() { + // Outputs a 16 digit numbers + let program = vec![1102,34915192,34915192,7,4,7,99,0]; + let mut c = Computer::initialize(program, vec![]); + c.run(); + assert_eq!(c.output[0].to_string().len(), 16); + } + + #[test] + fn relative_example_3() { + // Outputs 1125899906842624 + let program = vec![104,1125899906842624,99]; + let mut c = Computer::initialize(program, vec![]); + c.run(); + assert_eq!(c.output[0], 1125899906842624); + } + + #[test] + fn day9_relative_mode_input() { + let program = vec![109, -2, 203, 2, 99]; + let mut c = Computer::initialize(program, vec![1312]); + c.run(); + assert_eq!(c.mem_get(0), 1312); + } + + #[test] + fn day9() { + let program = vec![1102,34463338,34463338,63,1007,63,34463338,63,1005,63,53,1101,0,3,1000,109,988,209,12,9,1000,209,6,209,3,203,0,1008,1000,1,63,1005,63,65,1008,1000,2,63,1005,63,904,1008,1000,0,63,1005,63,58,4,25,104,0,99,4,0,104,0,99,4,17,104,0,99,0,0,1102,1,432,1027,1101,439,0,1026,1101,0,36,1010,1101,0,34,1018,1102,278,1,1029,1101,0,24,1002,1102,1,20,1016,1102,1,31,1011,1102,319,1,1024,1102,21,1,1012,1102,1,763,1022,1102,1,25,1007,1101,0,287,1028,1102,32,1,1008,1101,0,22,1013,1102,38,1,1001,1101,0,314,1025,1102,35,1,1009,1102,1,23,1015,1102,39,1,1019,1102,27,1,1000,1102,1,37,1003,1102,1,28,1017,1101,0,0,1020,1101,0,29,1004,1102,1,30,1006,1102,1,756,1023,1102,1,33,1005,1101,0,1,1021,1102,26,1,1014,109,13,2108,28,-7,63,1005,63,201,1001,64,1,64,1105,1,203,4,187,1002,64,2,64,109,8,21107,40,41,-3,1005,1018,225,4,209,1001,64,1,64,1105,1,225,1002,64,2,64,109,-3,1206,2,239,4,231,1105,1,243,1001,64,1,64,1002,64,2,64,109,-21,1201,6,0,63,1008,63,35,63,1005,63,267,1001,64,1,64,1105,1,269,4,249,1002,64,2,64,109,35,2106,0,-4,4,275,1001,64,1,64,1105,1,287,1002,64,2,64,109,-11,1205,-1,303,1001,64,1,64,1105,1,305,4,293,1002,64,2,64,109,8,2105,1,-5,4,311,1106,0,323,1001,64,1,64,1002,64,2,64,109,-7,21108,41,38,-6,1005,1016,339,1106,0,345,4,329,1001,64,1,64,1002,64,2,64,109,2,21102,42,1,-8,1008,1016,45,63,1005,63,369,1001,64,1,64,1105,1,371,4,351,1002,64,2,64,109,-14,21101,43,0,1,1008,1011,43,63,1005,63,397,4,377,1001,64,1,64,1106,0,397,1002,64,2,64,109,-8,21101,44,0,8,1008,1010,47,63,1005,63,417,1105,1,423,4,403,1001,64,1,64,1002,64,2,64,109,25,2106,0,0,1001,64,1,64,1105,1,441,4,429,1002,64,2,64,109,-20,2107,37,-6,63,1005,63,463,4,447,1001,64,1,64,1106,0,463,1002,64,2,64,109,8,2108,25,-8,63,1005,63,485,4,469,1001,64,1,64,1106,0,485,1002,64,2,64,109,-1,21107,45,44,-1,1005,1013,505,1001,64,1,64,1106,0,507,4,491,1002,64,2,64,109,-11,1207,-1,25,63,1005,63,529,4,513,1001,64,1,64,1106,0,529,1002,64,2,64,109,23,1206,-5,545,1001,64,1,64,1106,0,547,4,535,1002,64,2,64,109,-31,2102,1,5,63,1008,63,27,63,1005,63,569,4,553,1106,0,573,1001,64,1,64,1002,64,2,64,109,27,21102,46,1,-9,1008,1013,46,63,1005,63,595,4,579,1105,1,599,1001,64,1,64,1002,64,2,64,109,-26,2101,0,6,63,1008,63,24,63,1005,63,625,4,605,1001,64,1,64,1106,0,625,1002,64,2,64,109,5,1208,0,37,63,1005,63,645,1001,64,1,64,1105,1,647,4,631,1002,64,2,64,109,7,2102,1,-3,63,1008,63,31,63,1005,63,671,1001,64,1,64,1105,1,673,4,653,1002,64,2,64,109,2,1202,-5,1,63,1008,63,33,63,1005,63,699,4,679,1001,64,1,64,1105,1,699,1002,64,2,64,109,-4,2101,0,-3,63,1008,63,35,63,1005,63,719,1105,1,725,4,705,1001,64,1,64,1002,64,2,64,109,-5,1207,4,32,63,1005,63,741,1106,0,747,4,731,1001,64,1,64,1002,64,2,64,109,29,2105,1,-7,1001,64,1,64,1106,0,765,4,753,1002,64,2,64,109,-26,2107,36,5,63,1005,63,781,1105,1,787,4,771,1001,64,1,64,1002,64,2,64,109,10,1201,-6,0,63,1008,63,32,63,1005,63,809,4,793,1106,0,813,1001,64,1,64,1002,64,2,64,109,3,21108,47,47,-5,1005,1012,835,4,819,1001,64,1,64,1106,0,835,1002,64,2,64,109,-24,1202,9,1,63,1008,63,25,63,1005,63,859,1001,64,1,64,1106,0,861,4,841,1002,64,2,64,109,19,1205,9,875,4,867,1106,0,879,1001,64,1,64,1002,64,2,64,109,-3,1208,-1,32,63,1005,63,897,4,885,1106,0,901,1001,64,1,64,4,64,99,21102,27,1,1,21101,915,0,0,1105,1,922,21201,1,60043,1,204,1,99,109,3,1207,-2,3,63,1005,63,964,21201,-2,-1,1,21102,1,942,0,1106,0,922,21202,1,1,-1,21201,-2,-3,1,21101,957,0,0,1106,0,922,22201,1,-1,-2,1105,1,968,22102,1,-2,-2,109,-3,2105,1,0]; + let mut c = Computer::initialize(program, vec![1]); + c.run(); + assert_eq!(c.output.len(), 1); + assert_eq!(c.output[0], 3063082071); + } +}