Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <ctype.h>
- #include <stdint.h>
- char **get_lines_n(const char *filename, int *len) {
- FILE *f = fopen(filename, "r");
- fseek(f, 0, SEEK_END);
- long fsize = ftell(f);
- fseek(f, 0, SEEK_SET);
- char *string = malloc(fsize + 1);
- fread(string, 1, fsize, f);
- fclose(f);
- string[fsize] = 0;
- int i, blks = 0;
- char **lines = malloc(101 * sizeof(char *));
- char *line;
- char *str, *saveptr;
- for(i = 0, str = string; ; i++, str = NULL) {
- if(i >= 100) {
- i = 0;
- blks++;
- lines = realloc(lines, (100 * (1 + blks) + 1) * sizeof(char *));
- }
- char *tmp = strtok_r(str, "\n", &saveptr);
- if(tmp == NULL) {
- lines[100*blks + i] = NULL;
- break;
- }
- line = malloc(sizeof(char) * (strlen(tmp)+1));
- strcpy(line, tmp);
- lines[100*blks + i] = line;
- }
- *len = i;
- free(string);
- return lines;
- }
- char **get_lines(const char *filename) {
- int foo;
- return get_lines_n(filename, &foo);
- }
- void free_lines(char **lines) {
- int i = 0;
- char *line = lines[0];
- while(line != NULL) {
- free(line);
- line = lines[++i];
- }
- free(lines);
- }
- typedef struct instruction {
- int opcode;
- int arg1;
- int arg2;
- } instruction;
- void part23() {
- int len;
- char **lines = get_lines_n("23.txt", &len);
- char *line, *saveptr;
- int i = 0;
- instruction *instructions = malloc(sizeof(instruction) * len);
- /* "Opcodes":
- 0 - hlf
- 1 - tpl
- 2 - inc
- 3 - jmp
- 4 - jie
- 5 - jio
- Arguments are registers (0: a, 1: b) or offsets
- */
- while(lines[i] != NULL) {
- line = lines[i];
- int opcode;
- char *ins = strtok_r(line, " ", &saveptr);
- switch(ins[0]) {
- case 'h':
- opcode = 0;
- break;
- case 't':
- opcode = 1;
- break;
- case 'i':
- opcode = 2;
- break;
- case 'j':
- if(ins[1] == 'm') {
- opcode = 3;
- } else if(ins[2] == 'e') {
- opcode = 4;
- } else {
- opcode = 5;
- } break;
- }
- instructions[i].opcode = opcode;
- ins = strtok_r(NULL, ",", &saveptr);
- if(ins[0] == 'a')
- instructions[i].arg1 = 0;
- else if(ins[0] == 'b')
- instructions[i].arg1 = 1;
- else
- instructions[i].arg1 = atoi(ins);
- if(opcode == 4 || opcode == 5)
- instructions[i].arg2 = atoi(strtok_r(NULL, ",", &saveptr));
- i++;
- }
- int part2 = 0;
- int a;
- again: a = part2;
- int b = 0;
- int ip = 0;
- int r;
- while(ip >= 0 && ip < len) {
- instruction cur = instructions[ip];
- if(cur.opcode == 0) {
- if(cur.arg1)
- b /= 2;
- else
- a /= 2;
- ip++;
- } else if(cur.opcode == 1) {
- if(cur.arg1)
- b *= 3;
- else
- a *= 3;
- ip++;
- } else if(cur.opcode == 2) {
- if(cur.arg1)
- b++;
- else
- a++;
- ip++;
- } else if(cur.opcode == 3) {
- ip += cur.arg1;
- } else if(cur.opcode == 4) {
- r = (cur.arg1) ? b : a;
- if(r % 2 == 0)
- ip += cur.arg2;
- else
- ip++;
- } else {
- r = (cur.arg1) ? b : a;
- if(r == 1)
- ip += cur.arg2;
- else
- ip++;
- }
- }
- printf("%d\n", b);
- if(!part2) {
- part2 = 1;
- goto again;
- }
- free_lines(lines);
- free(instructions);
- }
- void reverse(int n[], int len) {
- int start = 0;
- int end = len;
- while(start < end) {
- int tmp = n[start];
- n[start] = n[end];
- n[end--] = tmp;
- start++;
- }
- }
- int min_count = 100;
- long long min_product = INT_MAX;
- int nums[30];
- void recursive_search(int offset, int remaining, int count, long long product) {
- if(count > min_count)
- return;
- while(nums[offset] != 0) {
- if(nums[offset] > remaining) {
- ;
- }
- else if(nums[offset] == remaining) {
- if(count < min_count) {
- min_count = count;
- min_product = product * nums[offset];
- } else if(count == min_count) {
- if(product * nums[offset] < min_product)
- min_product = product * nums[offset];
- }
- }
- else {
- recursive_search(offset + 1, remaining - nums[offset], count + 1, product * nums[offset]);
- }
- offset++;
- }
- }
- void part24() {
- char **lines = get_lines("24.txt");
- int i = 0;
- while(lines[i] != NULL) {
- nums[i] = atoi(lines[i]);
- free(lines[i++]);
- }
- nums[i] = 0;
- reverse(nums, i-1);
- int sum = 0;
- for(i = 0; nums[i] != 0; i++)
- sum += nums[i];
- sum /= 3;
- free(lines);
- recursive_search(1, sum - nums[0], 2, nums[0]);
- printf("%I64d\n", min_product);
- min_count = 100;
- min_product = INT_MAX;
- sum *= 3;
- sum /= 4;
- recursive_search(1, sum - nums[0], 2, nums[0]);
- printf("%I64d\n", min_product);
- }
- void part25() {
- char **lines = get_lines("25.txt");
- char *line = lines[0];
- int i = 0;
- while(!isdigit(line[i++]));
- int x = atoi(line + i - 1);
- while(isdigit(line[i++]));
- while(!isdigit(line[i++]));
- int y = atoi(line + i - 1);
- free(line);
- free(lines);
- int num = (x+y) * (x+y) - (x+y);
- num = num >> 1;
- num += 1-x;
- uint64_t result = 20151125;
- for(i = 1; i < num; i++) {
- result *= 252533;
- result %= 33554393;
- }
- printf("%I64d\n", result); // Change to %llu on *nix systems
- }
- int main() {
- part23();
- //part24();
- //part25();
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement