From caeaa98e9f31c2124f251a5da7c6496d9175f165 Mon Sep 17 00:00:00 2001 From: "Dr. Matthias Ratajczak" Date: Tue, 9 Aug 2022 20:29:38 +0200 Subject: [PATCH] add solution for 50 --- euler50/Cargo.toml | 12 +++++ euler50/src/main.rs | 113 ++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 125 insertions(+) create mode 100644 euler50/Cargo.toml create mode 100644 euler50/src/main.rs diff --git a/euler50/Cargo.toml b/euler50/Cargo.toml new file mode 100644 index 0000000..df1b20a --- /dev/null +++ b/euler50/Cargo.toml @@ -0,0 +1,12 @@ +[package] +name = "euler50" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] + +[profile.release] +lto = true +opt-level = 3 diff --git a/euler50/src/main.rs b/euler50/src/main.rs new file mode 100644 index 0000000..c3866f5 --- /dev/null +++ b/euler50/src/main.rs @@ -0,0 +1,113 @@ +use std::collections::HashSet; + +// you will probably need to incrase the stack limit +// $ ulimit -s +// $ ulimit -s 32768 + +type Int = i64; +const MIN_VALUE: Int = 2; +const MAX_VALUE: Int = 1_000_000; +const SIZE: usize = (MAX_VALUE - MIN_VALUE) as usize; +type Array = [bool; SIZE]; + +fn main() { + println!("Getting prime numbers up to {}", MAX_VALUE); + let primes = Primes::from_array(get_prime_numbers_array()); + println!("Starting to iterate ..."); + let result = find_using_iter(&primes).unwrap(); + println!( + "{:?} / sum: {} / len: {}", + result, + sum_of_vector(result), + result.len() + ); +} + +fn get_prime_numbers_array() -> Array { + // Sieve of Eratosthenes + let mut result = [true; SIZE]; + for number_to_check in MIN_VALUE..(MAX_VALUE / 2) { + let mut last_number = number_to_check; + loop { + let current_number = last_number + number_to_check; + if current_number >= MAX_VALUE { + break; + } + result[(current_number - MIN_VALUE) as usize] = false; + last_number = current_number; + } + } + result +} + +fn sum_of_vector(vector: &[Int]) -> Int { + vector.iter().sum() +} + +struct Primes { + vector: Vec, + set: HashSet, +} + +struct PrimesIter<'a> { + primes: &'a Primes, + current_min: usize, + current_len: usize, +} + +impl<'a> Iterator for PrimesIter<'a> { + type Item = &'a [Int]; + + fn next(&mut self) -> Option { + let result = &self.primes.vector[self.current_min..(self.current_min + self.current_len)]; + if result.iter().sum::() > MAX_VALUE { + self.decrement_search_length(); + return self.next(); + } + if self.current_min + self.current_len < self.primes.vector.len() { + self.current_min += 1; + } else { + self.decrement_search_length(); + } + Some(result) + } +} + +impl<'a> PrimesIter<'a> { + fn decrement_search_length(&mut self) { + self.current_min = 0; + self.current_len -= 1; + println!("{}", self.current_len); + } +} + +impl Primes { + fn iter(&self) -> PrimesIter { + PrimesIter { + primes: self, + current_min: 0, + current_len: self.vector.len(), + } + } + + fn from_array(array: Array) -> Primes { + let mut vector = Vec::new(); + let mut set = HashSet::new(); + for number in MIN_VALUE..MAX_VALUE { + if array[(number - MIN_VALUE) as usize] { + vector.push(number); + set.insert(number); + } + } + Primes { vector, set } + } +} + +fn find_using_iter(primes: &'_ Primes) -> Option<&'_ [Int]> { + for subvector in primes.iter() { + if primes.set.contains(&sum_of_vector(subvector)) { + return Some(subvector); + } + } + None +}