Skip to content

Commit 5a738ab

Browse files
committed
Use bits in the inner parts of part2
1 parent 8f20215 commit 5a738ab

File tree

1 file changed

+92
-72
lines changed

1 file changed

+92
-72
lines changed

src/day6.rs

Lines changed: 92 additions & 72 deletions
Original file line numberDiff line numberDiff line change
@@ -98,62 +98,66 @@ fn try_opst_up(
9898
start_x: usize,
9999
start_y: usize,
100100

101-
hor_grid: &mut [[u8; SIZE]; SIZE],
102-
vert_grid: &mut [[u8; SIZE]; SIZE],
101+
hor_grid: &mut [BitArray<[u64; SIZE.div_ceil(64)]>; SIZE],
102+
vert_grid: &mut [BitArray<[u64; SIZE.div_ceil(64)]>; SIZE],
103103

104104
mut visited_vert: BitArray<[u64; (SIZE * SIZE).div_ceil(64)]>,
105105
mut visited_hor: BitArray<[u64; (SIZE * SIZE).div_ceil(64)]>,
106106
) -> bool {
107-
hor_grid[opst_y][opst_x] = b'#';
108-
vert_grid[opst_x][opst_y] = b'#';
107+
hor_grid[opst_y].set(opst_x, true);
108+
vert_grid[opst_x].set(opst_y, true);
109109

110110
let mut x = start_x;
111111
let mut y = start_y;
112112

113113
let loops = loop {
114114
// Up
115-
let Some(y_move) = memchr::memrchr(b'#', &vert_grid[x][..y]) else {
115+
let y_move = vert_grid[x][..y].trailing_zeros();
116+
if y_move >= y {
116117
break false;
117-
};
118-
y = y_move + 1;
118+
}
119+
y -= y_move;
119120
if visited_vert[y * SIZE + x] {
120121
break true;
121122
}
122123
visited_vert.set(y * SIZE + x, true);
123124

124125
// Right
125-
let Some(x_move) = memchr::memchr(b'#', &hor_grid[y][x + 1..]) else {
126+
let x_move = hor_grid[y][x + 1..].leading_zeros();
127+
if x + x_move > SIZE {
126128
break false;
127-
};
129+
}
128130
x += x_move;
129131
if visited_hor[y * SIZE + x] {
130132
break true;
131133
}
132134
visited_hor.set(y * SIZE + x, true);
133135

134136
// Down
135-
let Some(y_move) = memchr::memchr(b'#', &vert_grid[x][y + 1..]) else {
137+
let y_move = vert_grid[x][y + 1..].leading_zeros();
138+
if y + y_move > SIZE {
136139
break false;
137-
};
140+
}
138141
y += y_move;
139142
if visited_vert[y * SIZE + x] {
140143
break true;
141144
}
142145
visited_vert.set(y * SIZE + x, true);
143146

144147
// Left
145-
let Some(x_move) = memchr::memrchr(b'#', &hor_grid[y][..x]) else {
148+
let x_move = hor_grid[y][..x].trailing_zeros();
149+
if x_move >= x {
146150
break false;
147-
};
148-
x = x_move + 1;
151+
}
152+
x -= x_move;
149153
if visited_hor[y * SIZE + x] {
150154
break true;
151155
}
152156
visited_hor.set(y * SIZE + x, true);
153157
};
154158

155-
hor_grid[opst_y][opst_x] = 0;
156-
vert_grid[opst_x][opst_y] = 0;
159+
hor_grid[opst_y].set(opst_x, false);
160+
vert_grid[opst_x].set(opst_y, false);
157161

158162
loops
159163
}
@@ -164,62 +168,66 @@ fn try_opst_right(
164168
start_x: usize,
165169
start_y: usize,
166170

167-
hor_grid: &mut [[u8; SIZE]; SIZE],
168-
vert_grid: &mut [[u8; SIZE]; SIZE],
171+
hor_grid: &mut [BitArray<[u64; SIZE.div_ceil(64)]>; SIZE],
172+
vert_grid: &mut [BitArray<[u64; SIZE.div_ceil(64)]>; SIZE],
169173

170174
mut visited_vert: BitArray<[u64; (SIZE * SIZE).div_ceil(64)]>,
171175
mut visited_hor: BitArray<[u64; (SIZE * SIZE).div_ceil(64)]>,
172176
) -> bool {
173-
hor_grid[opst_y][opst_x] = b'#';
174-
vert_grid[opst_x][opst_y] = b'#';
177+
hor_grid[opst_y].set(opst_x, true);
178+
vert_grid[opst_x].set(opst_y, true);
175179

176180
let mut x = start_x;
177181
let mut y = start_y;
178182

179183
let loops = loop {
180184
// Right
181-
let Some(x_move) = memchr::memchr(b'#', &hor_grid[y][x + 1..]) else {
185+
let x_move = hor_grid[y][x + 1..].leading_zeros();
186+
if x + x_move > SIZE {
182187
break false;
183-
};
188+
}
184189
x += x_move;
185190
if visited_hor[y * SIZE + x] {
186191
break true;
187192
}
188193
visited_hor.set(y * SIZE + x, true);
189194

190195
// Down
191-
let Some(y_move) = memchr::memchr(b'#', &vert_grid[x][y + 1..]) else {
196+
let y_move = vert_grid[x][y + 1..].leading_zeros();
197+
if y + y_move > SIZE {
192198
break false;
193-
};
199+
}
194200
y += y_move;
195201
if visited_vert[y * SIZE + x] {
196202
break true;
197203
}
198204
visited_vert.set(y * SIZE + x, true);
199205

200206
// Left
201-
let Some(x_move) = memchr::memrchr(b'#', &hor_grid[y][..x]) else {
207+
let x_move = hor_grid[y][..x].trailing_zeros();
208+
if x_move >= x {
202209
break false;
203-
};
204-
x = x_move + 1;
210+
}
211+
x -= x_move;
205212
if visited_hor[y * SIZE + x] {
206213
break true;
207214
}
208215
visited_hor.set(y * SIZE + x, true);
209216

210217
// Up
211-
let Some(y_move) = memchr::memrchr(b'#', &vert_grid[x][..y]) else {
218+
let y_move = vert_grid[x][..y].trailing_zeros();
219+
if y_move >= y {
212220
break false;
213-
};
214-
y = y_move + 1;
221+
}
222+
y -= y_move;
215223
if visited_vert[y * SIZE + x] {
216224
break true;
217225
}
218226
visited_vert.set(y * SIZE + x, true);
219227
};
220228

221-
hor_grid[opst_y][opst_x] = 0;
222-
vert_grid[opst_x][opst_y] = 0;
229+
hor_grid[opst_y].set(opst_x, false);
230+
vert_grid[opst_x].set(opst_y, false);
223231

224232
loops
225233
}
@@ -230,62 +238,66 @@ fn try_opst_down(
230238
start_x: usize,
231239
start_y: usize,
232240

233-
hor_grid: &mut [[u8; SIZE]; SIZE],
234-
vert_grid: &mut [[u8; SIZE]; SIZE],
241+
hor_grid: &mut [BitArray<[u64; SIZE.div_ceil(64)]>; SIZE],
242+
vert_grid: &mut [BitArray<[u64; SIZE.div_ceil(64)]>; SIZE],
235243

236244
mut visited_vert: BitArray<[u64; (SIZE * SIZE).div_ceil(64)]>,
237245
mut visited_hor: BitArray<[u64; (SIZE * SIZE).div_ceil(64)]>,
238246
) -> bool {
239-
hor_grid[opst_y][opst_x] = b'#';
240-
vert_grid[opst_x][opst_y] = b'#';
247+
hor_grid[opst_y].set(opst_x, true);
248+
vert_grid[opst_x].set(opst_y, true);
241249

242250
let mut x = start_x;
243251
let mut y = start_y;
244252

245253
let loops = loop {
246254
// Down
247-
let Some(y_move) = memchr::memchr(b'#', &vert_grid[x][y + 1..]) else {
255+
let y_move = vert_grid[x][y + 1..].leading_zeros();
256+
if y + y_move > SIZE {
248257
break false;
249-
};
258+
}
250259
y += y_move;
251260
if visited_vert[y * SIZE + x] {
252261
break true;
253262
}
254263
visited_vert.set(y * SIZE + x, true);
255264

256265
// Left
257-
let Some(x_move) = memchr::memrchr(b'#', &hor_grid[y][..x]) else {
266+
let x_move = hor_grid[y][..x].trailing_zeros();
267+
if x_move >= x {
258268
break false;
259-
};
260-
x = x_move + 1;
269+
}
270+
x -= x_move;
261271
if visited_hor[y * SIZE + x] {
262272
break true;
263273
}
264274
visited_hor.set(y * SIZE + x, true);
265275

266276
// Up
267-
let Some(y_move) = memchr::memrchr(b'#', &vert_grid[x][..y]) else {
277+
let y_move = vert_grid[x][..y].trailing_zeros();
278+
if y_move >= y {
268279
break false;
269-
};
270-
y = y_move + 1;
280+
}
281+
y -= y_move;
271282
if visited_vert[y * SIZE + x] {
272283
break true;
273284
}
274285
visited_vert.set(y * SIZE + x, true);
275286

276287
// Right
277-
let Some(x_move) = memchr::memchr(b'#', &hor_grid[y][x + 1..]) else {
288+
let x_move = hor_grid[y][x + 1..].leading_zeros();
289+
if x + x_move > SIZE {
278290
break false;
279-
};
291+
}
280292
x += x_move;
281293
if visited_hor[y * SIZE + x] {
282294
break true;
283295
}
284296
visited_hor.set(y * SIZE + x, true);
285297
};
286298

287-
hor_grid[opst_y][opst_x] = 0;
288-
vert_grid[opst_x][opst_y] = 0;
299+
hor_grid[opst_y].set(opst_x, false);
300+
vert_grid[opst_x].set(opst_y, false);
289301

290302
loops
291303
}
@@ -296,62 +308,66 @@ fn try_opst_left(
296308
start_x: usize,
297309
start_y: usize,
298310

299-
hor_grid: &mut [[u8; SIZE]; SIZE],
300-
vert_grid: &mut [[u8; SIZE]; SIZE],
311+
hor_grid: &mut [BitArray<[u64; SIZE.div_ceil(64)]>; SIZE],
312+
vert_grid: &mut [BitArray<[u64; SIZE.div_ceil(64)]>; SIZE],
301313

302314
mut visited_vert: BitArray<[u64; (SIZE * SIZE).div_ceil(64)]>,
303315
mut visited_hor: BitArray<[u64; (SIZE * SIZE).div_ceil(64)]>,
304316
) -> bool {
305-
hor_grid[opst_y][opst_x] = b'#';
306-
vert_grid[opst_x][opst_y] = b'#';
317+
hor_grid[opst_y].set(opst_x, true);
318+
vert_grid[opst_x].set(opst_y, true);
307319

308320
let mut x = start_x;
309321
let mut y = start_y;
310322

311323
let loops = loop {
312324
// Left
313-
let Some(x_move) = memchr::memrchr(b'#', &hor_grid[y][..x]) else {
325+
let x_move = hor_grid[y][..x].trailing_zeros();
326+
if x_move >= x {
314327
break false;
315-
};
316-
x = x_move + 1;
328+
}
329+
x -= x_move;
317330
if visited_hor[y * SIZE + x] {
318331
break true;
319332
}
320333
visited_hor.set(y * SIZE + x, true);
321334

322335
// Up
323-
let Some(y_move) = memchr::memrchr(b'#', &vert_grid[x][..y]) else {
336+
let y_move = vert_grid[x][..y].trailing_zeros();
337+
if y_move >= y {
324338
break false;
325-
};
326-
y = y_move + 1;
339+
}
340+
y -= y_move;
327341
if visited_vert[y * SIZE + x] {
328342
break true;
329343
}
330344
visited_vert.set(y * SIZE + x, true);
331345

332346
// Right
333-
let Some(x_move) = memchr::memchr(b'#', &hor_grid[y][x + 1..]) else {
347+
let x_move = hor_grid[y][x + 1..].leading_zeros();
348+
if x + x_move > SIZE {
334349
break false;
335-
};
350+
}
336351
x += x_move;
337352
if visited_hor[y * SIZE + x] {
338353
break true;
339354
}
340355
visited_hor.set(y * SIZE + x, true);
341356

342357
// Down
343-
let Some(y_move) = memchr::memchr(b'#', &vert_grid[x][y + 1..]) else {
358+
let y_move = vert_grid[x][y + 1..].leading_zeros();
359+
if y + y_move > SIZE {
344360
break false;
345-
};
361+
}
346362
y += y_move;
347363
if visited_vert[y * SIZE + x] {
348364
break true;
349365
}
350366
visited_vert.set(y * SIZE + x, true);
351367
};
352368

353-
hor_grid[opst_y][opst_x] = 0;
354-
vert_grid[opst_x][opst_y] = 0;
369+
hor_grid[opst_y].set(opst_x, false);
370+
vert_grid[opst_x].set(opst_y, false);
355371

356372
loops
357373
}
@@ -362,6 +378,8 @@ pub fn part2(s: &str) -> u32 {
362378

363379
let mut hor_grid = [[0u8; SIZE]; SIZE];
364380
let mut vert_grid = [[0u8; SIZE]; SIZE];
381+
let mut hor_grid_bits = [BitArray::<[u64; SIZE.div_ceil(64)]>::default(); SIZE];
382+
let mut vert_grid_bits = [BitArray::<[u64; SIZE.div_ceil(64)]>::default(); SIZE];
365383

366384
let mut visited_vert = BitArray::<[u64; (SIZE * SIZE).div_ceil(64)]>::default();
367385
let mut visited_hor = BitArray::<[u64; (SIZE * SIZE).div_ceil(64)]>::default();
@@ -373,6 +391,8 @@ pub fn part2(s: &str) -> u32 {
373391

374392
hor_grid[y][x] = b'#';
375393
vert_grid[x][y] = b'#';
394+
hor_grid_bits[y].set(x, true);
395+
vert_grid_bits[x].set(y, true);
376396
}
377397

378398
let start = memchr::memchr(b'^', s).unwrap();
@@ -400,8 +420,8 @@ pub fn part2(s: &str) -> u32 {
400420
y - 1,
401421
x,
402422
y,
403-
&mut hor_grid,
404-
&mut vert_grid,
423+
&mut hor_grid_bits,
424+
&mut vert_grid_bits,
405425
visited_vert.clone(),
406426
visited_hor.clone(),
407427
) {
@@ -428,8 +448,8 @@ pub fn part2(s: &str) -> u32 {
428448
y,
429449
x,
430450
y,
431-
&mut hor_grid,
432-
&mut vert_grid,
451+
&mut hor_grid_bits,
452+
&mut vert_grid_bits,
433453
visited_vert.clone(),
434454
visited_hor.clone(),
435455
) {
@@ -456,8 +476,8 @@ pub fn part2(s: &str) -> u32 {
456476
y + 1,
457477
x,
458478
y,
459-
&mut hor_grid,
460-
&mut vert_grid,
479+
&mut hor_grid_bits,
480+
&mut vert_grid_bits,
461481
visited_vert.clone(),
462482
visited_hor.clone(),
463483
) {
@@ -484,8 +504,8 @@ pub fn part2(s: &str) -> u32 {
484504
y,
485505
x,
486506
y,
487-
&mut hor_grid,
488-
&mut vert_grid,
507+
&mut hor_grid_bits,
508+
&mut vert_grid_bits,
489509
visited_vert.clone(),
490510
visited_hor.clone(),
491511
) {

0 commit comments

Comments
 (0)