166 lines
4.1 KiB
C
166 lines
4.1 KiB
C
|
#include <stdio.h>
|
||
|
#include <stdlib.h>
|
||
|
#include <string.h>
|
||
|
#include <stdint.h>
|
||
|
#include <gmp.h>
|
||
|
|
||
|
typedef struct Monkey_ Monkey;
|
||
|
|
||
|
typedef struct Monkey_ {
|
||
|
mpz_t item[64];
|
||
|
int items, is_multiply, opertant_is_old, operant, test, test_true, test_false, inspections;
|
||
|
} Monkey;
|
||
|
|
||
|
Monkey* newMonkey()
|
||
|
{
|
||
|
char *line = NULL;
|
||
|
size_t size;
|
||
|
size_t len;
|
||
|
Monkey *monkey = malloc(sizeof(Monkey));
|
||
|
monkey->inspections = 0;
|
||
|
// items
|
||
|
len = getline(&line, &size, stdin);
|
||
|
|
||
|
char *begin = line+18;
|
||
|
char *token = NULL;
|
||
|
for (int j = 0; (token = strsep(&begin, ",")); j++)
|
||
|
{
|
||
|
// printf("%u: %s\n", j, token);
|
||
|
// monkey->item[j] = atoi(token);
|
||
|
mpz_init_set_str(monkey->item[j], token, 10);
|
||
|
monkey->items = j+1;
|
||
|
}
|
||
|
|
||
|
// operation
|
||
|
len = getline(&line, &size, stdin);
|
||
|
monkey->is_multiply = line[23] == '*';
|
||
|
monkey->opertant_is_old = line[25] == 'o';
|
||
|
if (!monkey->opertant_is_old)
|
||
|
{
|
||
|
monkey->operant = atoi(line+25);
|
||
|
}
|
||
|
|
||
|
// test
|
||
|
len = getline(&line, &size, stdin);
|
||
|
monkey->test = atoi(line+21);
|
||
|
|
||
|
// test true
|
||
|
len = getline(&line, &size, stdin);
|
||
|
monkey->test_true = atoi(line+29);
|
||
|
|
||
|
// test true
|
||
|
len = getline(&line, &size, stdin);
|
||
|
monkey->test_false = atoi(line+30);
|
||
|
|
||
|
len = getline(&line, &size, stdin);
|
||
|
return monkey;
|
||
|
}
|
||
|
|
||
|
void inspect(Monkey *monkey, Monkey *monkeys[])
|
||
|
{
|
||
|
monkey->inspections += monkey->items;
|
||
|
for (int i = 0; i < monkey->items; i++)
|
||
|
{
|
||
|
// set operant
|
||
|
mpz_t operant; //= monkey->operant;
|
||
|
mpz_init_set_si(operant, monkey->operant);
|
||
|
if (monkey->opertant_is_old)
|
||
|
mpz_init_set(operant, monkey->item[i]);
|
||
|
// operant = monkey->item[i];
|
||
|
|
||
|
// set operation
|
||
|
if (monkey->is_multiply)
|
||
|
{
|
||
|
// monkey->item[i] *= operant;
|
||
|
mpz_mul(monkey->item[i], monkey->item[i], operant);
|
||
|
} else {
|
||
|
// monkey->item[i] += operant;
|
||
|
mpz_add(monkey->item[i], monkey->item[i], operant);
|
||
|
}
|
||
|
|
||
|
// monkey->item[i] /= 3;
|
||
|
|
||
|
// throw item based on test
|
||
|
int throw = monkey->test_true;
|
||
|
if (!mpz_divisible_ui_p(monkey->item[i], monkey->test))
|
||
|
{
|
||
|
throw = monkey->test_false;
|
||
|
}
|
||
|
|
||
|
// monkeys[throw]->item[monkeys[throw]->items] = monkey->item[i];
|
||
|
mpz_set(monkeys[throw]->item[monkeys[throw]->items], monkey->item[i]);
|
||
|
monkeys[throw]->items++;
|
||
|
}
|
||
|
monkey->items = 0;
|
||
|
}
|
||
|
|
||
|
int main()
|
||
|
{
|
||
|
|
||
|
int monkeys = 0;
|
||
|
Monkey *monkey[10] = { };
|
||
|
|
||
|
char *line = NULL;
|
||
|
size_t size;
|
||
|
size_t len;
|
||
|
long long active1 = 0, active2 = 0;
|
||
|
|
||
|
while ((len = getline(&line, &size, stdin)) != -1)
|
||
|
{
|
||
|
// create monkeys
|
||
|
Monkey *new = newMonkey();
|
||
|
monkey[monkeys] = new;
|
||
|
monkeys++;
|
||
|
|
||
|
// print monkey attributes
|
||
|
printf("Items:");
|
||
|
for (int i = 0; i < new->items; i++)
|
||
|
{
|
||
|
printf("%lud ", new->item[i]);
|
||
|
}
|
||
|
printf("\n %d %d %d %d %d %d\n\n",
|
||
|
new->is_multiply,
|
||
|
new->opertant_is_old,
|
||
|
new->operant,
|
||
|
new->test,
|
||
|
new->test_true,
|
||
|
new->test_false
|
||
|
);
|
||
|
}
|
||
|
|
||
|
for (int i = 0; i < 10000; i++)
|
||
|
{
|
||
|
// do inspection
|
||
|
for (int ii = 0; ii < monkeys; ii++)
|
||
|
{
|
||
|
inspect(monkey[ii], monkey);
|
||
|
}
|
||
|
|
||
|
// output rounds
|
||
|
printf("Round %d\n", i);
|
||
|
// for (int ii = 0; ii < monkeys; ii++)
|
||
|
// {
|
||
|
// printf("Monkey %d: ", ii);
|
||
|
// for (int iii = 0; iii < monkey[ii]->items; iii++)
|
||
|
// {
|
||
|
// printf("%lu ", monkey[ii]->item[iii]);
|
||
|
// }
|
||
|
// printf("\n");
|
||
|
// }
|
||
|
}
|
||
|
|
||
|
// get two most active monkeys
|
||
|
for (int i = 0; i < monkeys; i++)
|
||
|
{
|
||
|
if (monkey[i]->inspections > active1)
|
||
|
{
|
||
|
active2 = active1;
|
||
|
active1 = monkey[i]->inspections;
|
||
|
}
|
||
|
printf("Monkey %d inspected items %d times. \n", i, monkey[i]->inspections);
|
||
|
}
|
||
|
|
||
|
printf("Monkey biz: \n%lld\n", active1 * active2);
|
||
|
}
|
||
|
|