Replace binary search with maths

This commit is contained in:
2023-12-07 21:45:20 +01:00
parent f5ca9af74b
commit e1c23385c9

View File

@@ -47,21 +47,17 @@ fn parse_long_race(i: &[u8]) -> IResult<&[u8], (u64, u64)> {
} }
fn ways(time: u64, distance: u64) -> u64 { fn ways(time: u64, distance: u64) -> u64 {
let half = time / 2; let a = -1.0;
let mut min = 1; let b = time as f64;
let mut max = half; let c = -(distance as f64);
let d = b * b - 4.0 * a * c;
while min < max { if d < 0.0 {
let mid = min + (max - min) / 2; 0
if mid * (time - mid) <= distance {
min = mid + 1;
} else { } else {
max = mid; // Note: can leave out quite a bit of the quadratic formula because things cancel out nicely
} let solution = ((b - d.sqrt()) / 2.0 + 1.0).floor() as u64;
} let half = time / 2;
let make_it = half - solution + 1;
let make_it = half - min + 1;
if time % 2 == 0 { if time % 2 == 0 {
2 * make_it - 1 2 * make_it - 1
@@ -69,6 +65,7 @@ fn ways(time: u64, distance: u64) -> u64 {
2 * make_it 2 * make_it
} }
} }
}
pub fn part1(input: &[u8]) -> anyhow::Result<String> { pub fn part1(input: &[u8]) -> anyhow::Result<String> {
let (time, distance) = parse_input(input, parse_race)?; let (time, distance) = parse_input(input, parse_race)?;