1
0
Fork 0

Optimized day 14 solution by using a stack and only reusing data from previous iterations rather than simulating each particle from the top to it's final position

This commit is contained in:
Ishan Jain 2022-12-14 17:41:50 +05:30
parent 7f255cab2c
commit c3f94ad140
Signed by: ishan
GPG Key ID: 0506DB2A1CC75C27
2 changed files with 47 additions and 38 deletions

View File

@ -60,30 +60,34 @@ enum Node {
fn solution((mut input, lowest): ([Node; ARR_SIZE], usize)) -> usize { fn solution((mut input, lowest): ([Node; ARR_SIZE], usize)) -> usize {
let mut count = 0; let mut count = 0;
let mut stack = Vec::with_capacity(ROW_SIZE);
let (mut px, mut py) = (500, 0);
loop { loop {
let (mut px, mut py) = (500, 0);
for y in 0..=lowest {
py = y;
if input[(py + 1) * ROW_SIZE + px] == Node::Empty {
continue;
} else if input[(py + 1) * ROW_SIZE + px - 1] == Node::Empty {
px -= 1;
} else if input[(py + 1) * ROW_SIZE + px + 1] == Node::Empty {
px += 1;
} else {
break;
};
}
if py >= lowest { if py >= lowest {
break; break;
} }
let k = (py + 1) * ROW_SIZE + px;
input[py * ROW_SIZE + px] = Node::Sand; (px, py) = if input[k] == Node::Empty {
count += 1; stack.push((px, py));
(px, py + 1)
} else if input[k - 1] == Node::Empty {
stack.push((px, py));
(px - 1, py + 1)
} else if input[k + 1] == Node::Empty {
stack.push((px, py));
(px + 1, py + 1)
} else {
input[py * ROW_SIZE + px] = Node::Sand;
count += 1;
match stack.pop() {
Some(v) => v,
None => break,
}
};
} }
count count

View File

@ -62,31 +62,36 @@ enum Node {
} }
fn solution(mut input: [Node; ARR_SIZE]) -> usize { fn solution(mut input: [Node; ARR_SIZE]) -> usize {
let mut count = 1; // Include the source of sand in this count let mut count = 0;
let mut stack = Vec::with_capacity(ROW_SIZE);
let (mut px, mut py) = (500, 0);
loop { loop {
let (mut px, mut py) = (500, 0); if py + 1 >= ROW_SIZE {
loop {
if input[(py + 1) * ROW_SIZE + px] == Node::Empty {
py += 1;
} else if input[(py + 1) * ROW_SIZE + px - 1] == Node::Empty {
py += 1;
px -= 1;
} else if input[(py + 1) * ROW_SIZE + px + 1] == Node::Empty {
py += 1;
px += 1;
} else {
break;
};
}
if px == 500 && py == 0 {
break; break;
} }
input[py * ROW_SIZE + px] = Node::Sand; let k = (py + 1) * ROW_SIZE + px;
count += 1;
(px, py) = if input[k] == Node::Empty {
stack.push((px, py));
(px, py + 1)
} else if input[k - 1] == Node::Empty {
stack.push((px, py));
(px - 1, py + 1)
} else if input[k + 1] == Node::Empty {
stack.push((px, py));
(px + 1, py + 1)
} else {
input[py * ROW_SIZE + px] = Node::Sand;
count += 1;
match stack.pop() {
Some(v) => v,
None => break,
}
};
} }
count count