1
0

wash day07
Some checks failed
Build and test / test (push) Failing after 2m40s

This commit is contained in:
xeals 2023-12-07 17:19:51 +11:00
parent 221cad1136
commit 300ceb885f
Signed by: xeals
SSH Key Fingerprint: SHA256:pRv+8swQDA+/LuZ7NHj9m006BbKexlNK62OUA01ZZBc

View File

@ -4,18 +4,14 @@ const mem = std.mem;
pub fn main() !void { pub fn main() !void {
const input = @embedFile("data/day07.txt"); const input = @embedFile("data/day07.txt");
const sln = try solve2(util.gpa, input); const part1 = try solve(util.gpa, input, jack);
std.debug.print("{d}\n", .{sln.a}); const part2 = try solve(util.gpa, input, joker);
std.debug.print("{d}\n", .{sln.b}); std.debug.print("{d}\n", .{part1});
std.debug.print("{d}\n", .{part2});
} }
const Cards = [5]u8; const Cards = [5]u8;
const Solution = struct {
a: usize,
b: usize,
};
const Score = enum(u8) { const Score = enum(u8) {
fiveKind, fiveKind,
fourKind, fourKind,
@ -32,13 +28,16 @@ const Hand = struct {
score: Score, score: Score,
}; };
fn fixCards(cards: *[5]u8) void { const jack = 10;
const joker = 0;
fn fixCards(cards: *[5]u8, jValue: u8) void {
for (cards, 0..) |card, i| { for (cards, 0..) |card, i| {
cards[i] = switch (card) { cards[i] = switch (card) {
'A' => 13, 'A' => 13,
'K' => 12, 'K' => 12,
'Q' => 11, 'Q' => 11,
'J' => 0, 'J' => jValue,
'T' => 9, 'T' => 9,
'2'...'9' => card - '1', '2'...'9' => card - '1',
else => unreachable, else => unreachable,
@ -52,24 +51,6 @@ fn u8gt(context: void, a: u8, b: u8) bool {
} }
fn scoreHand(cards: Cards) Score { fn scoreHand(cards: Cards) Score {
var dups: [14]u8 = undefined;
@memset(&dups, 0);
for (cards) |a| {
dups[a] += 1;
}
std.mem.sort(u8, &dups, {}, u8gt);
return switch (dups[0]) {
5 => .fiveKind,
4 => .fourKind,
3 => if (dups[1] == 2) .fullHouse else .threeKind,
2 => if (dups[1] == 2) .twoPair else .onePair,
else => .high,
};
}
const joker = 0;
fn scoreHand2(cards: Cards) Score {
var jokers: usize = 0; var jokers: usize = 0;
var dups: [14]u8 = undefined; var dups: [14]u8 = undefined;
@memset(&dups, 0); @memset(&dups, 0);
@ -80,7 +61,7 @@ fn scoreHand2(cards: Cards) Score {
dups[a] += 1; dups[a] += 1;
} }
} }
std.mem.sort(u8, &dups, {}, u8gt); mem.sort(u8, &dups, {}, u8gt);
return switch (dups[0] + jokers) { return switch (dups[0] + jokers) {
5 => .fiveKind, 5 => .fiveKind,
4 => .fourKind, 4 => .fourKind,
@ -102,64 +83,28 @@ fn compareHand(context: void, a: Hand, b: Hand) bool {
unreachable; unreachable;
} }
fn sortHands(hands: *std.ArrayList(Hand)) !void { fn solve(alloc: mem.Allocator, input: []const u8, jValue: u8) !u32 {
std.mem.sort(Hand, hands.items, {}, compareHand);
}
fn solve(alloc: mem.Allocator, input: []const u8) !Solution {
var hands = try std.ArrayList(Hand).initCapacity(alloc, 1001); var hands = try std.ArrayList(Hand).initCapacity(alloc, 1001);
defer hands.deinit(); defer hands.deinit();
var it = util.splitLines(input); var it = util.splitLines(input);
while (it.next()) |line| { while (it.next()) |line| {
if (line.len == 0) continue; if (line.len == 0) continue;
var cards = line[0..5].*; var cards = line[0..5].*;
fixCards(&cards); fixCards(&cards, jValue);
const bid = try std.fmt.parseInt(u32, line[6..], 10); const bid = try std.fmt.parseInt(u32, line[6..], 10);
const score = scoreHand(cards); const score = scoreHand(cards);
const hand = Hand{ .cards = cards, .bid = bid, .score = score }; try hands.append(.{ .cards = cards, .bid = bid, .score = score });
try hands.append(hand);
} }
// std.debug.print("{any}\n", .{hands.items}); mem.sort(Hand, hands.items, {}, compareHand);
try sortHands(&hands);
var partA: usize = 0; var winnings: u32 = 0;
for (hands.items, 1..) |hand, rank| { for (hands.items, 1..) |hand, rank| {
// std.debug.print("{d} * {d}\n", .{ hand.bid, rank }); winnings += hand.bid * @as(u32, @intCast(rank));
partA += hand.bid * rank;
} }
return .{ .a = partA, .b = 0 }; return winnings;
}
fn solve2(alloc: mem.Allocator, input: []const u8) !Solution {
var hands = try std.ArrayList(Hand).initCapacity(alloc, 1001);
defer hands.deinit();
var it = util.splitLines(input);
while (it.next()) |line| {
if (line.len == 0) continue;
var cards = line[0..5].*;
fixCards(&cards);
const bid = try std.fmt.parseInt(u32, line[6..], 10);
const score = scoreHand2(cards);
const hand = Hand{ .cards = cards, .bid = bid, .score = score };
try hands.append(hand);
}
// std.debug.print("{any}\n", .{hands.items});
try sortHands(&hands);
var partB: usize = 0;
for (hands.items, 1..) |hand, rank| {
// std.debug.print("{d} * {d}\n", .{ hand.bid, rank });
partB += hand.bid * rank;
}
return .{ .a = 0, .b = partB };
} }
test "silver" { test "silver" {
@ -170,8 +115,8 @@ test "silver" {
\\KTJJT 220 \\KTJJT 220
\\QQQJA 483 \\QQQJA 483
; ;
const sln = try solve(std.testing.allocator, input); const sln = try solve(std.testing.allocator, input, jack);
try std.testing.expectEqual(@as(usize, 6440), sln.a); try std.testing.expectEqual(@as(usize, 6440), sln);
} }
test "gold" { test "gold" {
@ -182,6 +127,6 @@ test "gold" {
\\KTJJT 220 \\KTJJT 220
\\QQQJA 483 \\QQQJA 483
; ;
const sln = try solve2(std.testing.allocator, input); const sln = try solve(std.testing.allocator, input, joker);
try std.testing.expectEqual(@as(usize, 5905), sln.b); try std.testing.expectEqual(@as(usize, 5905), sln);
} }