aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorkaiwu <kaiwu2004@gmail.com>2022-04-21 23:44:52 +0800
committerkaiwu <kaiwu2004@gmail.com>2022-04-21 23:44:52 +0800
commitc9d7af596862557c0ea5495eef8fd7c970f6372f (patch)
tree58c17808e6b799c352e224e901bf8ac0c1548a8d /src
parent1b5efbb1a8d71b9fc2668315229370a26e0e9d18 (diff)
downloadadvent-of-code-c9d7af596862557c0ea5495eef8fd7c970f6372f.tar.gz
advent-of-code-c9d7af596862557c0ea5495eef8fd7c970f6372f.zip
loopback computer
Diffstat (limited to 'src')
-rw-r--r--src/2019/day5/aoc.cpp16
-rw-r--r--src/2019/day5/aoc.h4
-rw-r--r--src/2019/day7/aoc.cpp64
3 files changed, 66 insertions, 18 deletions
diff --git a/src/2019/day5/aoc.cpp b/src/2019/day5/aoc.cpp
index cf2f65c..8a33a4c 100644
--- a/src/2019/day5/aoc.cpp
+++ b/src/2019/day5/aoc.cpp
@@ -84,17 +84,17 @@ static size_t opt8(std::vector<int>& codes, std::vector<int>& outputs, size_t i,
}
typedef size_t (*opt_f)(std::vector<int>&, std::vector<int>&, size_t, int, int);
-static void run(size_t i, std::vector<int>& codes, std::vector<int>& outputs, interrupt_f f) {
+static void run(size_t i, std::vector<int>& codes, std::vector<int>& outputs, interrupt_f f, void* p) {
// printf("execute %d at %zu\n", codes[i], i);
static opt_f opts[] = {opt1, opt2, opt3, opt4, opt5, opt6, opt7, opt8};
if (codes[i] != 99) {
int m1{0}, m2{0};
int m = mode(codes[i], &m1, &m2);
int x = opts[m - 1](codes, outputs, i, m1, m2);
- if (f == nullptr) {
- run(x, codes, outputs, f);
- } else {
- f(x, outputs);
+
+ bool stop = f != nullptr && f(x, outputs, p);
+ if (!stop) {
+ run(x, codes, outputs, f, p);
}
}
}
@@ -112,12 +112,12 @@ void set_computer(int* i) {
int run_computer(std::vector<int> codes) {
std::vector<int> outputs;
- run(0, codes, outputs, nullptr);
+ run(0, codes, outputs, nullptr, nullptr);
return outputs[outputs.size() - 1];
}
-void run_computer(size_t i, std::vector<int> codes, std::vector<int>& outputs, interrupt_f f) {
- run(i, codes, outputs, f);
+void run_computer(size_t i, std::vector<int>& codes, std::vector<int>& outputs, interrupt_f f, void* p) {
+ run(i, codes, outputs, f, p);
}
std::pair<int, int> day5(line_view file) {
diff --git a/src/2019/day5/aoc.h b/src/2019/day5/aoc.h
index a93de6e..5e4a1a8 100644
--- a/src/2019/day5/aoc.h
+++ b/src/2019/day5/aoc.h
@@ -8,8 +8,8 @@ namespace aoc2019 {
void set_computer(int* i);
int run_computer(std::vector<int> codes);
-typedef void (*interrupt_f)(size_t, std::vector<int>&);
-void run_computer(size_t i, std::vector<int> codes, std::vector<int>&, interrupt_f);
+typedef bool (*interrupt_f)(size_t, std::vector<int>&, void *);
+void run_computer(size_t i, std::vector<int>& codes, std::vector<int>&, interrupt_f, void *);
std::pair<int, int> day5(line_view);
}
diff --git a/src/2019/day7/aoc.cpp b/src/2019/day7/aoc.cpp
index 8976f28..b2842ea 100644
--- a/src/2019/day7/aoc.cpp
+++ b/src/2019/day7/aoc.cpp
@@ -46,6 +46,26 @@ static void get_number(const char** pp, int* d) {
*pp = p;
}
+struct check_t {
+ int* a;
+ int* b;
+};
+
+bool interrupt(size_t i, std::vector<int>& outputs, void* out) {
+ if (outputs.size() > 0) {
+ check_t* x = (check_t*)out;
+ if (x->b - x->a == 12) {
+ *(x->b + 2) = i;
+ *(x->a + 1) = outputs[0];
+ } else {
+ *(x->b + 2) = i;
+ *(x->b + 4) = outputs[0];
+ }
+ return true;
+ }
+ return false;
+}
+
std::pair<int, int> day7(line_view file) {
std::vector<int> codes;
const char* p = file.line;
@@ -62,16 +82,44 @@ std::pair<int, int> day7(line_view file) {
std::set<int> ns1;
find_max(is1, 0, ns1, &m1, codes);
- for (int i : {5, 6, 7, 8, 9}) {
- int is2[10] = {0};
- is2[0] = i;
- is2[1] = 33;
- set_computer(is2);
- std::vector<int> outputs;
- run_computer(0, codes, outputs, nullptr);
- std::for_each(outputs.begin(), outputs.end(), [](int x) { printf("%d ", x); });
+ auto print = [](int* is) {
+ for (size_t i = 0; i < 15; i++) {
+ printf("%d ", is[i]);
+ }
printf("\n");
+ };
+
+ auto copy = [](int* s1, int* s2) {
+ for (int i = 0; i < 15; i++) {
+ s1[i] = s2[i];
+ }
+ };
+
+ auto equal = [](int* s1, int* s2) -> bool {
+ for (int i = 0; i < 15; i++) {
+ if (s1[i] != s2[i]) {
+ return false;
+ }
+ }
+ return true;
+ };
+
+ int is2[15] = {9, 0, 0, 7, 0, 0, 8, 0, 0, 5, 0, 0, 6, 0, 0};
+ int is3[15] = {0};
+ std::vector<int> cs[] = {codes, codes, codes, codes, codes};
+ bool stop{false};
+ while (!stop) {
+ copy(is3, is2);
+ for (size_t i = 0; i < ARRAY_SIZE(is2); i += 3) {
+ std::vector<int> outputs;
+ check_t chk{is2, &is2[i]};
+ is2[i + 2] == 0 ? set_computer(&is2[i]) : set_computer(&is2[i + 1]);
+ run_computer(is2[i + 2], cs[i / 3], outputs, interrupt, &chk);
+ }
+ stop = equal(is3, is2);
+ print(is2);
}
+ printf("%d\n", is2[1]);
return {m1, 0};
}