From ce5a46dde407e9264bd8cf7d1b58911d875b3dd1 Mon Sep 17 00:00:00 2001 From: Juan Pablo Yamamoto Date: Sat, 20 Jan 2024 17:56:57 -0600 Subject: [PATCH] day 25 --- Cargo.lock | 166 +++++++++++++++++++++++++++++++++++++++++++++++++- Cargo.toml | 1 + README.md | 3 +- src/bin/25.rs | 70 +++++++++++++++++++++ 4 files changed, 238 insertions(+), 2 deletions(-) create mode 100644 src/bin/25.rs diff --git a/Cargo.lock b/Cargo.lock index aa935c7..b0db5b5 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -23,15 +23,35 @@ version = "0.0.1" dependencies = [ "chrono", "dhat", - "itertools", + "itertools 0.12.0", "ndarray", "ndarray-linalg", "num", "pico-args", "rayon", + "rustworkx-core", "tinyjson", ] +[[package]] +name = "ahash" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77c3a9648d43b9cd48db467b3f87fdd6e146bcc88ab0180006cef2179fe11d01" +dependencies = [ + "cfg-if", + "getrandom", + "once_cell", + "version_check", + "zerocopy", +] + +[[package]] +name = "allocator-api2" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0942ffc6dcaadf03badf6e6a2d0228460359d5e34b57ccdc720b7382dfbd5ec5" + [[package]] name = "android-tzdata" version = "0.1.1" @@ -256,6 +276,12 @@ version = "1.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a26ae43d7bcc3b814de94796a5e736d4029efb0ee900c12e2d54c993ad1a1e07" +[[package]] +name = "equivalent" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5" + [[package]] name = "errno" version = "0.3.8" @@ -284,6 +310,12 @@ dependencies = [ "windows-sys", ] +[[package]] +name = "fixedbitset" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0ce7134b9999ecaf8bcd65542e436736ef32ddca1b3e06094cb6ec5755203b80" + [[package]] name = "flate2" version = "1.0.28" @@ -335,6 +367,23 @@ version = "0.28.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4271d37baee1b8c7e4b708028c57d816cf9d2434acb33a549475f78c181f6253" +[[package]] +name = "hashbrown" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" + +[[package]] +name = "hashbrown" +version = "0.14.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "290f1a1d9242c78d09ce40a5e87e7554ee637af1351968159f4952f028f75604" +dependencies = [ + "ahash", + "allocator-api2", + "rayon", +] + [[package]] name = "iana-time-zone" version = "0.1.58" @@ -368,6 +417,36 @@ dependencies = [ "unicode-normalization", ] +[[package]] +name = "indexmap" +version = "1.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bd070e393353796e801d209ad339e89596eb4c8d430d18ede6a1cced8fafbd99" +dependencies = [ + "autocfg", + "hashbrown 0.12.3", +] + +[[package]] +name = "indexmap" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d530e1a18b1cb4c484e6e34556a0d948706958449fca0cab753d649f2bce3d1f" +dependencies = [ + "equivalent", + "hashbrown 0.14.3", + "rayon", +] + +[[package]] +name = "itertools" +version = "0.10.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b0fd2260e829bddf4cb6ea802289de2f86d6a7a690192fbe91b3f46e0f2c8473" +dependencies = [ + "either", +] + [[package]] name = "itertools" version = "0.12.0" @@ -757,6 +836,16 @@ version = "2.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" +[[package]] +name = "petgraph" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e1d3afd2628e69da2be385eb6f2fd57c8ac7977ceeff6dc166ff1657b0e386a9" +dependencies = [ + "fixedbitset", + "indexmap 2.1.0", +] + [[package]] name = "pico-args" version = "0.5.0" @@ -775,6 +864,16 @@ version = "0.2.17" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de" +[[package]] +name = "priority-queue" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fff39edfcaec0d64e8d0da38564fad195d2d51b680940295fcc307366e101e61" +dependencies = [ + "autocfg", + "indexmap 1.9.3", +] + [[package]] name = "proc-macro2" version = "1.0.70" @@ -823,6 +922,15 @@ dependencies = [ "getrandom", ] +[[package]] +name = "rand_pcg" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "59cad018caf63deb318e5a4586d99a24424a364f40f1e5778c29aca23f4fc73e" +dependencies = [ + "rand_core", +] + [[package]] name = "rawpointer" version = "0.2.1" @@ -839,6 +947,17 @@ dependencies = [ "rayon-core", ] +[[package]] +name = "rayon-cond" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9ac2a28c5317e6d26ac87a8629c0eb362690ed1d739f4040e21cfaafdf04e6f8" +dependencies = [ + "either", + "itertools 0.10.5", + "rayon", +] + [[package]] name = "rayon-core" version = "1.12.0" @@ -915,6 +1034,25 @@ dependencies = [ "base64", ] +[[package]] +name = "rustworkx-core" +version = "0.13.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72abf7976bc09a30391248b3c6509338b235c02b0e9b0bf8af686c289cad3f45" +dependencies = [ + "ahash", + "fixedbitset", + "hashbrown 0.14.3", + "indexmap 2.1.0", + "num-traits", + "petgraph", + "priority-queue", + "rand", + "rand_pcg", + "rayon", + "rayon-cond", +] + [[package]] name = "ryu" version = "1.0.16" @@ -1161,6 +1299,12 @@ version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" +[[package]] +name = "version_check" +version = "0.9.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" + [[package]] name = "walkdir" version = "2.4.0" @@ -1404,3 +1548,23 @@ dependencies = [ "linux-raw-sys", "rustix", ] + +[[package]] +name = "zerocopy" +version = "0.7.32" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74d4d3961e53fa4c9a25a8637fc2bfaf2595b3d3ae34875568a5cf64787716be" +dependencies = [ + "zerocopy-derive", +] + +[[package]] +name = "zerocopy-derive" +version = "0.7.32" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9ce1b18ccd8e73a9321186f97e46f9f04b778851177567b1975109d26a08d2a6" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.41", +] diff --git a/Cargo.toml b/Cargo.toml index 8bc4b33..04b5962 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -33,3 +33,4 @@ itertools = "0.12.0" num = "0.4.1" ndarray = "0.15.6" ndarray-linalg = { version = "0.16", features = ["openblas-static"] } +rustworkx-core = "0.13.2" diff --git a/README.md b/README.md index 765f86a..78f984d 100644 --- a/README.md +++ b/README.md @@ -64,8 +64,9 @@ Solutions for [Advent of Code](https://adventofcode.com/) in [Rust](https://www. | [Day 22](./src/bin/22.rs) | `9.5ms` | `17.6ms` | | [Day 23](./src/bin/23.rs) | `2.3ms` | `1.7s` | | [Day 24](./src/bin/24.rs) | `20.1ms` | `154.2µs` | +| [Day 25](./src/bin/25.rs) | `380.2ms` | `-` | -**Total: 48331.47ms** +**Total: 48711.67ms** --- diff --git a/src/bin/25.rs b/src/bin/25.rs new file mode 100644 index 0000000..3a93a5c --- /dev/null +++ b/src/bin/25.rs @@ -0,0 +1,70 @@ +use std::convert::Infallible; +use std::collections::HashMap; +use rustworkx_core::connectivity::stoer_wagner_min_cut; +use rustworkx_core::petgraph::Undirected; +use rustworkx_core::petgraph::csr::Csr; + +advent_of_code::solution!(25); + +type Graph<'a> = Csr<&'a str, (), Undirected>; + +fn parse_wiring(input: &str) -> (&str, Vec<&str>) { + let (key, wires) = input.split_once(": ").unwrap(); + (key, wires.split_ascii_whitespace().collect()) +} + +fn parse(input: &str) -> Graph { + let wires = input.lines() + .map(|l| parse_wiring(l)) + .collect::>(); + + let mut nodes: HashMap<&str, u32> = HashMap::new(); + let mut graph = Csr::new(); + + for (wire, _) in wires.iter() { + nodes.insert(wire, graph.add_node(*wire)); + } + + for (wire, conns) in wires { + let wire_idx = nodes[wire]; + + for conn in conns { + let conn_idx = nodes.entry(conn).or_insert_with(|| graph.add_node(conn)); + graph.add_edge(wire_idx, *conn_idx, ()); + } + } + + graph +} + +pub fn part_one(input: &str) -> Option { + let graph = parse(input); + + let (_, connected_set) = stoer_wagner_min_cut(&graph, |_| Ok::(1)).unwrap().unwrap(); + + let size1 = connected_set.len(); + let size2 = graph.node_count() - size1; + + Some((size1 * size2) as u32) +} + +pub fn part_two(_input: &str) -> Option { + None +} + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn test_part_one() { + let result = part_one(&advent_of_code::template::read_file("examples", DAY)); + assert_eq!(result, Some(54)); + } + + #[test] + fn test_part_two() { + let result = part_two(&advent_of_code::template::read_file("examples", DAY)); + assert_eq!(result, None); + } +}