parent
baf74f24dd
commit
c1bfd5fd5d
@ -1,10 +1,13 @@ |
||||
# Generated by Cargo |
||||
# will have compiled files and executables |
||||
/target/ |
||||
*/target/ |
||||
|
||||
# Remove Cargo.lock from gitignore if creating an executable, leave it for libraries |
||||
# More information here https://doc.rust-lang.org/cargo/guide/cargo-toml-vs-cargo-lock.html |
||||
Cargo.lock |
||||
*/Cargo.lock |
||||
|
||||
# These are backup files generated by rustfmt |
||||
**/*.rs.bk |
||||
|
||||
*.in |
||||
*.out |
||||
|
@ -0,0 +1,9 @@ |
||||
[package] |
||||
name = "day01-hard" |
||||
version = "0.1.0" |
||||
authors = ["inga-lovinde <52715130+inga-lovinde@users.noreply.github.com>"] |
||||
edition = "2018" |
||||
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html |
||||
|
||||
[dependencies] |
@ -0,0 +1,34 @@ |
||||
use std::io::{self, BufRead}; |
||||
|
||||
// non-negative numbers are presorted, largest first
|
||||
fn check(numbers: &[u32], remaining_count: u32, remaining_sum: u32, current_product: u64) -> () { |
||||
if remaining_count == 0 { |
||||
if remaining_sum == 0 { |
||||
println!("{}", current_product); |
||||
} |
||||
|
||||
return; |
||||
} |
||||
|
||||
for (i, &number) in numbers.iter().enumerate() { |
||||
if number * remaining_count < remaining_sum { |
||||
return; |
||||
} |
||||
|
||||
if number <= remaining_sum { |
||||
check(&numbers[i..], remaining_count - 1, remaining_sum - number, current_product * (number as u64)); |
||||
} |
||||
} |
||||
} |
||||
|
||||
fn main() { |
||||
let stdin = io::stdin(); |
||||
let mut source_numbers: Vec<_> = stdin.lock().lines().into_iter() |
||||
.map(|line| line.unwrap().parse::<u32>().unwrap()) |
||||
.collect(); |
||||
|
||||
source_numbers.sort(); |
||||
source_numbers.reverse(); |
||||
|
||||
check(&source_numbers, 3, 2020, 1); |
||||
} |
@ -0,0 +1,9 @@ |
||||
[package] |
||||
name = "day01" |
||||
version = "0.1.0" |
||||
authors = ["inga-lovinde <52715130+inga-lovinde@users.noreply.github.com>"] |
||||
edition = "2018" |
||||
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html |
||||
|
||||
[dependencies] |
@ -0,0 +1,20 @@ |
||||
use std::collections::HashSet; |
||||
use std::io::{self, BufRead}; |
||||
|
||||
// Could be solved in O(n)
|
||||
// (sort two copies of the list and walk it from the opposite ends to find a match)
|
||||
// But O(n*log(n)) solution is much simpler.
|
||||
fn main() { |
||||
let stdin = io::stdin(); |
||||
let source_numbers: Vec<_> = stdin.lock().lines().into_iter() |
||||
.map(|line| line.unwrap().parse::<u32>().unwrap()) |
||||
.collect(); |
||||
|
||||
let first_set: HashSet<_> = source_numbers.iter().map(|&number| number).collect(); |
||||
let second_set: HashSet<_> = source_numbers.iter().map(|&number| 2020-number).collect(); |
||||
|
||||
let result = first_set.intersection(&second_set); |
||||
for value in result { |
||||
println!("{}", value * (2020-value)); |
||||
} |
||||
} |
@ -0,0 +1,11 @@ |
||||
[package] |
||||
name = "day02" |
||||
version = "0.1.0" |
||||
authors = ["inga-lovinde <52715130+inga-lovinde@users.noreply.github.com>"] |
||||
edition = "2018" |
||||
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html |
||||
|
||||
[dependencies] |
||||
lazy_static = "1.4.0" |
||||
regex = "1" |
@ -0,0 +1,61 @@ |
||||
use std::io::{self, BufRead}; |
||||
use std::error::Error; |
||||
use std::str::FromStr; |
||||
|
||||
#[macro_use] extern crate lazy_static; |
||||
use regex::Regex; |
||||
|
||||
struct LineInfo { |
||||
first_number: usize, |
||||
second_number: usize, |
||||
ch: char, |
||||
password: String, |
||||
} |
||||
|
||||
impl LineInfo { |
||||
fn is_valid_easy(&self) -> bool { |
||||
let count = self.password.chars().filter(|&password_char| password_char == self.ch).count(); |
||||
return self.first_number <= count && count <= self.second_number; |
||||
} |
||||
|
||||
fn is_valid_hard(&self) -> bool { |
||||
let chars: Vec<_> = self.password.chars().collect(); |
||||
return (chars[self.first_number-1] == self.ch) ^ (chars[self.second_number-1] == self.ch); |
||||
} |
||||
} |
||||
|
||||
impl FromStr for LineInfo { |
||||
type Err = Box<dyn Error>; |
||||
|
||||
fn from_str(s: &str) -> Result<Self, Self::Err> { |
||||
lazy_static! { |
||||
static ref LINE_RE: Regex = Regex::new(r"^(\d+)-(\d+)\s+([\S]):\s(.*)$").unwrap(); |
||||
} |
||||
|
||||
match LINE_RE.captures(s) { |
||||
Some(captures) => { |
||||
Ok(LineInfo { |
||||
first_number: captures[1].parse()?, |
||||
second_number: captures[2].parse()?, |
||||
ch: captures[3].chars().next().unwrap(), |
||||
password: captures[4].to_owned(), |
||||
}) |
||||
}, |
||||
_ => Err(Box::from("wrong string format")) |
||||
} |
||||
} |
||||
} |
||||
|
||||
fn main() { |
||||
let stdin = io::stdin(); |
||||
let lines: Vec<_> = stdin.lock().lines().into_iter() |
||||
.map(|line| line.unwrap().parse::<LineInfo>().unwrap()) |
||||
.collect(); |
||||
|
||||
println!("{}", lines.iter().filter(|line_info| line_info.is_valid_easy()).count()); |
||||
println!("{}", lines.iter().filter(|line_info| line_info.is_valid_hard()).count()); |
||||
|
||||
for line_info in lines { |
||||
println!("easy {}, hard {}: {}-{} {}: {}", line_info.is_valid_easy(), line_info.is_valid_hard(), line_info.first_number, line_info.second_number, line_info.ch, line_info.password); |
||||
} |
||||
} |
Loading…
Reference in new issue