This isn’t Lua code, Lua requires commas as separators for table items.
EDIT: Retracted, it seems like Lua allows this madness
Software developer and artist.
This isn’t Lua code, Lua requires commas as separators for table items.
EDIT: Retracted, it seems like Lua allows this madness
I hope it’s going to be used instead of machine learning. Seems much more correct, secure and efficient to me.
Nice and easy.
-- SPDX-FileCopyrightText: 2023 Jummit
--
-- SPDX-License-Identifier: GPL-3.0-or-later
local function nums(str)
local res = {}
for num in str:gmatch("%d+") do
res[num] = true
end
return res
end
local cards = {}
local points = 0
for line in io.open("4.input"):lines() do
local winning, have = line:match("Card%s*%d+: (.*) | (.*)")
winning = nums(winning)
have = nums(have)
local first = true
local score = 0
local matching = 0
for num in pairs(have) do
if winning[num] then
matching = matching + 1
if first then
first = false
score = score + 1
else
score = score * 2
end
end
end
points = points + score
table.insert(cards, {have=have, wins=matching, count=1})
end
print(points)
local cardSum = 0
for i, card in ipairs(cards) do
cardSum = cardSum + card.count
for n = i + 1, i + card.wins do
cards[n].count = cards[n].count + card.count
end
end
print(cardSum)
Input parsing AGAIN?
-- SPDX-FileCopyrightText: 2023 Jummit
--
-- SPDX-License-Identifier: GPL-3.0-or-later
local lines = {}
for line in io.open("3.input"):lines() do
table.insert(lines, "."..line..".")
end
local width = #lines[1]
local height = #lines
local function at(x, y, w)
if y < 1 or y > height then return nil end
return lines[y]:sub(x, x + w - 1)
end
local sum = 0
local gears = {}
for y, line in ipairs(lines) do
local start = 1
local outLine = line
while true do
local newStart, numEnd = line:find("%d+", start)
if not newStart then break end
local symbol = false
local num = tonumber(line:sub(newStart, numEnd))
for y = y - 1, y + 1 do
local surrounding = at(newStart - 1, y, numEnd - newStart + 3)
if surrounding then
if surrounding and surrounding:match("[^.%d]") then
symbol = true
end
for i = 1, #surrounding do
local gear = surrounding:sub(i, i) == "*"
if gear then
if not gears[y] then
gears[y] = {}
end
local x = i + newStart - 2
if not gears[y][x] then
gears[y][i + newStart - 2] = {}
end
table.insert(gears[y][x], num)
end
end
end
end
if symbol then
sum = sum + num
end
start = numEnd + 1
end
end
print(sum)
local ratio = 0
for _, line in pairs(gears) do
for _, gears in pairs(line) do
if #gears == 2 then
ratio = ratio + gears[1] * gears[2]
end
end
end
print(ratio)
// SPDX-FileCopyrightText: 2023 Jummit
//
// SPDX-License-Identifier: GPL-3.0-or-later
use strings;
use regex;
use fmt;
use os;
use bufio;
use io;
use strconv;
use types;
fn star_in(lines: []str, x: uint, y: uint, w: uint) bool = {
let start = y;
if (start > 0) start -= 1;
let end = y + 1;
if (end >= len(lines)) end -= 1;
const re = regex::compile(`[^.0-9]`)!;
for (let h = start; h <= end; h += 1) {
fmt::println(strings::sub(lines[h], x, x + w))!;
if (regex::test(&re, strings::sub(lines[h], x, x + w))) {
fmt::println("")!;
return true;
};
};
fmt::println("")!;
return false;
};
export fn main() void = {
const file = os::open("3.input")!;
defer io::close(file)!;
const buf = bufio::newscanner(file, types::SIZE_MAX);
let lines: []str = [];
defer strings::freeall(lines);
for (true) {
match (bufio::scan_line(&buf)!) {
case io::EOF =>
break;
case let line: const str =>
append(lines, strings::dup(line));
};
};
const height = len(lines);
const width = len(lines[0]);
let sum: uint = 0;
let gears: [](uint, uint) = [];
const num_re = regex::compile(`[0-9]+`)!;
for (let y = 0u; y < len(lines); y += 1) {
let nums = regex::findall(&num_re, lines[y]);
defer regex::result_freeall(nums);
for (let i = 0z; i < len(nums); i += 1) {
for (let j = 0z; j < len(nums[i]); j += 1) {
const find = nums[i][j];
const num = strconv::stou(find.content)!;
let start = find.start: uint;
let w = len(find.content): uint + 2;
if (start > 0) {
start -= 1;
} else {
w -= 1;
};
if (star_in(lines, start, y, w)) {
sum += num;
};
};
};
};
fmt::printfln("{}", sum)!;
};
Mostly an input parsing problem this time, but it was fun to use Hares tokenizer functions:
-- SPDX-FileCopyrightText: 2023 Jummit
--
-- SPDX-License-Identifier: GPL-3.0-or-later
local colors = {"blue", "red", "green"}
local available = {red = 12, blue = 14, green = 13}
local possible = 0
local id = 0
local min = 0
for game in io.open("2.input"):lines() do
id = id + 1
game = game:gsub("Game %d+: ", "").."; "
local max = {red = 0, blue = 0, green = 0}
for show in game:gmatch(".-; ") do
for _, color in ipairs(colors) do
local num = tonumber(show:match("(%d+) "..color))
if num then
max[color] = math.max(max[color], num)
end
end
end
min = min + max.red * max.blue * max.green
local thisPossible = true
for _, color in ipairs(colors) do
if max[color] > available[color] then
thisPossible = false
break
end
end
if thisPossible then
possible = possible + id
end
end
print(possible)
print(min)
// SPDX-FileCopyrightText: 2023 Jummit
//
// SPDX-License-Identifier: GPL-3.0-or-later
use strconv;
use types;
use strings;
use io;
use bufio;
use os;
use fmt;
const available: []uint = [12, 13, 14];
fn color_id(color: str) const uint = {
switch (color) {
case "red" => return 0;
case "green" => return 1;
case "blue" => return 2;
case => abort();
};
};
export fn main() void = {
const file = os::open("2.input")!;
defer io::close(file)!;
const scan = bufio::newscanner(file, types::SIZE_MAX);
let possible: uint = 0;
let min: uint = 0;
for (let id = 1u; true; id += 1) {
const line = match(bufio::scan_line(&scan)!) {
case io::EOF =>
break;
case let line: const str =>
yield strings::sub(
line,
strings::index(line, ": ") as size + 2,
strings::end);
};
let max: []uint = [0, 0, 0];
let tok = strings::rtokenize(line, "; ");
for (true) {
const show = match(strings::next_token(&tok)) {
case void =>
break;
case let show: str =>
yield show;
};
const pairs = strings::tokenize(show, ", ");
for (true) {
const pair: (str, str) = match(strings::next_token(&pairs)) {
case void =>
break;
case let pair: str =>
let tok = strings::tokenize(pair, " ");
yield (
strings::next_token(&tok) as str,
strings::next_token(&tok) as str
);
};
let color = color_id(pair.1);
let amount = strconv::stou(pair.0)!;
if (amount > max[color]) max[color] = amount;
};
};
if (max[0] <= available[0] && max[1] <= available[1] && max[2] <= available[2]) {
fmt::printfln("{}", id)!;
possible += id;
};
min += max[0] * max[1] * max[2];
};
fmt::printfln("{}", possible)!;
fmt::printfln("{}", min)!;
};
Trickier than expected! I ran into an issue with Lua patterns, so I had to revert to a more verbose solution, which I then used in Hare as well.
Lua:
-- SPDX-FileCopyrightText: 2023 Jummit
--
-- SPDX-License-Identifier: GPL-3.0-or-later
local sum = 0
for line in io.open("1.input"):lines() do
local a, b = line:match("^.-(%d).*(%d).-$")
if not a then
a = line:match("%d+")
b = a
end
if a and b then
sum = sum + tonumber(a..b)
end
end
print(sum)
local names = {
["one"] = 1,
["two"] = 2,
["three"] = 3,
["four"] = 4,
["five"] = 5,
["six"] = 6,
["seven"] = 7,
["eight"] = 8,
["nine"] = 9,
["1"] = 1,
["2"] = 2,
["3"] = 3,
["4"] = 4,
["5"] = 5,
["6"] = 6,
["7"] = 7,
["8"] = 8,
["9"] = 9,
}
sum = 0
for line in io.open("1.input"):lines() do
local firstPos = math.huge
local first
for name, num in pairs(names) do
local left = line:find(name)
if left and left < firstPos then
firstPos = left
first = num
end
end
local last
for i = #line, 1, -1 do
for name, num in pairs(names) do
local right = line:find(name, i)
if right then
last = num
goto found
end
end
end
::found::
sum = sum + tonumber(first * 10 + last)
end
print(sum)
Hare:
// SPDX-FileCopyrightText: 2023 Jummit
//
// SPDX-License-Identifier: GPL-3.0-or-later
use fmt;
use types;
use bufio;
use strings;
use io;
use os;
const numbers: [](str, int) = [
("one", 1),
("two", 2),
("three", 3),
("four", 4),
("five", 5),
("six", 6),
("seven", 7),
("eight", 8),
("nine", 9),
("1", 1),
("2", 2),
("3", 3),
("4", 4),
("5", 5),
("6", 6),
("7", 7),
("8", 8),
("9", 9),
];
fn solve(start: size) void = {
const file = os::open("1.input")!;
defer io::close(file)!;
const scan = bufio::newscanner(file, types::SIZE_MAX);
let sum = 0;
for (let i = 1u; true; i += 1) {
const line = match (bufio::scan_line(&scan)!) {
case io::EOF =>
break;
case let line: const str =>
yield line;
};
let first: (void | int) = void;
let last: (void | int) = void;
for (let i = 0z; i < len(line); i += 1) :found {
for (let num = start; num < len(numbers); num += 1) {
const start = strings::sub(line, i, strings::end);
if (first is void && strings::hasprefix(start, numbers[num].0)) {
first = numbers[num].1;
};
const end = strings::sub(line, len(line) - 1 - i, strings::end);
if (last is void && strings::hasprefix(end, numbers[num].0)) {
last = numbers[num].1;
};
if (first is int && last is int) {
break :found;
};
};
};
sum += first as int * 10 + last as int;
};
fmt::printfln("{}", sum)!;
};
export fn main() void = {
solve(9);
solve(0);
};
I’m going to use https://harelang.org to get more comfortable in it, and maybe my own languages, Otomescript and Hase.
Same here. Sounds pretty sustainable to me!
Of course the most productive comment is the least upvoted one. EDIT: After thinking about it, maybe it’s best to add an explanation to bare links.
Are you beginning to see things more clearly now?
It’s double speak. The translation is “We are evil and if you say something about what you see, we will silence you.”.
I’ve recently come to appreciate the “refactor the code while you write it” and “keep possible future changes in mind” ideas more and more. I think it really increases the probability that the system can live on instead of becoming obsolete.
Actually one of the few languages you can learn in its completeness in less than a day, so I wouldn’t really say it’s “hard to understand”. More like hard to read and understands programs written in it.
Sure, it’s advantageous in the short-term. I think this is where we misunderstand each other. What I’m trying to say is that under normal circumstances, individuals aren’t maximizing their output. They are just living as part of the community, following the unwritten rules and benefiting from that. (In the prisoner’s dilemma, this would be choice A).
If this is how everyone would act in their daily life, you would see crime, theft and abuse on an unimaginable level. No, people don’t always do what benefits them “at every individual point”. We are social creatures, acting as a community where the individuals benefit from working together. Although this has been successfully undermined by capitalism and other hierarchies.
This whole concept is also called, the Prisoner’s Dilemma, one of my favorite thought experiments because it shows how being rational can result in everyone being worse off.
Yes. The “tragedy of the commons” is a myth.
Without any limits, individual cattle owners have an incentive to overgraze the land, destroying its value to everybody.
This is factually false, because the land will be destroyed and individuals don’t benefit, not even in the short term. Commons work great (see open source software), but capitalism and power structures abuse and destroy them for short-term profit.
Interesting viewpoint, but I think the applications aren’t at fault: The operating system should ensure that the user has control of the computer at all times. I think you need to do three things to achieve that:
I guess really cold water isn’t really “wet” per-se. What did I just write…
What do you think the authors of the video don’t understand? You must have some insights if you say you understand AI better then everyone criticizing it.
Wow. Seems like I will never stop learning new things about Lua.