Add '2019/' from commit 'fc21396bc86bc0f706225f4f6e1d8294d344ca53'

git-subtree-dir: 2019
git-subtree-mainline: f1be11fca8
git-subtree-split: fc21396bc8
This commit is contained in:
2022-01-09 17:07:24 +00:00
36 changed files with 2978 additions and 0 deletions

89
2019/10/src/main.zig Normal file
View File

@@ -0,0 +1,89 @@
const std = @import("std");
// https://stackoverflow.com/a/328122
fn isBetween(a: Point, b: Point, c: Point) bool {
const crossproduct = (c.y - a.y) * (b.x - a.x) - (c.x - a.x) * (b.y - a.y);
// compare versus epsilon
if (std.math.absFloat(crossproduct) > std.math.f64_epsilon) return false;
const dotproduct = (c.x - a.x) * (b.x - a.x) + (c.y - a.y) * (b.y - a.y);
if (dotproduct < 0.0) return false;
const squaredlengthba = (b.x - a.x) * (b.x - a.x) + (b.y - a.y) * (b.y - a.y);
if (dotproduct > squaredlengthba) return false;
return true;
}
const Point = struct {
x: f64,
y: f64,
fn eql(self: Point, other: Point) bool {
return self.x == other.x and self.y == other.y;
}
};
const Asteroid = struct {
p: Point,
visible: usize = 0,
};
const Asteroids = std.ArrayList(Asteroid);
const input = @embedFile("../input");
fn part1(asteroids: Asteroids) void {
for (asteroids.toSlice()) |*a| {
for (asteroids.toSlice()) |b| {
if (a.p.eql(b.p)) continue;
// Check every asteroid to see if they fall between A and B
var blocked: bool = false;
for (asteroids.toSlice()) |c| {
if (a.p.eql(c.p) or b.p.eql(c.p)) continue;
//var dist = distToSegment(a.p, b.p, c.p);
if (isBetween(a.p, b.p, c.p)) {
blocked = true;
break;
}
}
// A can see B, so add it to A's score
if (!blocked) a.visible += 1;
}
}
var best: usize = 0;
for (asteroids.toSlice()) |asteroid| {
if (asteroid.visible > best) best = asteroid.visible;
}
std.debug.warn("Day 10, Part 1: {}\n", best);
}
pub fn main() anyerror!void {
var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);
defer arena.deinit();
const alloc = &arena.allocator;
var asteroids = Asteroids.init(alloc);
var lines = std.mem.separate(input, "\n");
var y: usize = 0;
while (lines.next()) |line| {
for (line) |byte, x| {
if (byte == '#') {
const px = @intToFloat(f64, x) + 0.5;
const py = @intToFloat(f64, y) + 0.5;
try asteroids.append(Asteroid{ .p = Point{ .x = px, .y = py } });
}
}
y += 1;
}
part1(asteroids);
}