67 lines
1.4 KiB
Rust
67 lines
1.4 KiB
Rust
pub fn one(input: String) {
|
|
let count = input
|
|
.lines()
|
|
.map(|line| to_numbers(line))
|
|
.filter(|numbers| is_safe(numbers))
|
|
.count();
|
|
println!("{}", count);
|
|
}
|
|
|
|
pub fn two(input: String) {
|
|
let count = input
|
|
.lines()
|
|
.map(|line| to_numbers(line))
|
|
.filter(|numbers| is_safe_corrected(numbers))
|
|
.count();
|
|
println!("{}", count);
|
|
}
|
|
|
|
fn to_numbers(line: &str) -> Vec<i32> {
|
|
line.split_whitespace()
|
|
.map(|n| n.parse().unwrap()) // All elements are numbers
|
|
.collect::<Vec<i32>>()
|
|
}
|
|
|
|
fn is_safe(numbers: &Vec<i32>) -> bool {
|
|
let first = numbers.first().unwrap();
|
|
let second = numbers.iter().nth(1).unwrap();
|
|
let incr = if second - first > 0 { 1 } else { -1 };
|
|
let mut cur = first;
|
|
for i in numbers.iter().skip(1) {
|
|
if !is_safe_interval(*cur, *i, incr) {
|
|
return false;
|
|
}
|
|
|
|
cur = i;
|
|
}
|
|
|
|
true
|
|
}
|
|
|
|
fn is_safe_corrected(numbers: &Vec<i32>) -> bool {
|
|
if is_safe(numbers) {
|
|
return true;
|
|
}
|
|
|
|
let count = numbers.len();
|
|
for i in 0..count {
|
|
let mut copy = numbers.clone();
|
|
copy.remove(i);
|
|
if is_safe(©) {
|
|
return true;
|
|
}
|
|
}
|
|
|
|
false
|
|
}
|
|
|
|
fn is_safe_interval(first: i32, second: i32, incr: i32) -> bool {
|
|
let diff = second - first;
|
|
if diff == 0 {
|
|
return false;
|
|
}
|
|
|
|
let norm = diff * incr;
|
|
norm > 0 && norm < 4
|
|
}
|