diff --git a/2019/Makefile b/2019/Makefile index 5897ce0..99c610c 100644 --- a/2019/Makefile +++ b/2019/Makefile @@ -1,8 +1,8 @@ FC:=gfortran -FFLAGS:=-Wall +FFLAGS:=-Wall -Wno-maybe-uninitialized BIN:=./bin SRC:=./src -BINS:=./bin/test.bin ./bin/day1.bin ./bin/day2.bin +BINS:=./bin/test.bin ./bin/day01.bin ./bin/day02.bin ./bin/day02b.bin all: aoc19 diff --git a/2019/data/day1a.txt b/2019/data/day01a.txt similarity index 100% rename from 2019/data/day1a.txt rename to 2019/data/day01a.txt diff --git a/2019/data/day02.txt b/2019/data/day02.txt new file mode 100644 index 0000000..e69de29 diff --git a/2019/data/day2a.txt b/2019/data/day02a.txt similarity index 100% rename from 2019/data/day2a.txt rename to 2019/data/day02a.txt diff --git a/2019/data/day02alarm.txt b/2019/data/day02alarm.txt new file mode 100644 index 0000000..458bdce --- /dev/null +++ b/2019/data/day02alarm.txt @@ -0,0 +1,2 @@ +1,12,2,3,1,1,2,3,1,3,4,3,1,5,0,3,2,13,1,19,1,9,19,23,2,23,13,27,1,27,9,31,2,31,6,35,1,5,35,39,1,10,39,43,2,43,6,47,1,10,47,51,2,6,51,55,1,5,55,59,1,59,9,63,1,13,63,67,2,6,67,71,1,5,71,75,2,6,75,79,2,79,6,83,1,13,83,87,1,9,87,91,1,9,91,95,1,5,95,99,1,5,99,103,2,13,103,107,1,6,107,111,1,9,111,115,2,6,115,119,1,13,119,123,1,123,6,127,1,127,5,131,2,10,131,135,2,135,10,139,1,13,139,143,1,10,143,147,1,2,147,151,1,6,151,0,99,2,14,0,0 + diff --git a/2019/data/day02ex1.txt b/2019/data/day02ex1.txt new file mode 100644 index 0000000..2912131 --- /dev/null +++ b/2019/data/day02ex1.txt @@ -0,0 +1 @@ +1,9,10,3,2,3,11,0,99,30,40,50 diff --git a/2019/data/day02ex2.txt b/2019/data/day02ex2.txt new file mode 100644 index 0000000..f4b112c --- /dev/null +++ b/2019/data/day02ex2.txt @@ -0,0 +1 @@ +1,1,1,4,99,5,6,0,99 diff --git a/2019/src/day1.f90 b/2019/src/day01.f90 similarity index 100% rename from 2019/src/day1.f90 rename to 2019/src/day01.f90 diff --git a/2019/src/day02.f90 b/2019/src/day02.f90 new file mode 100644 index 0000000..58f8d8e --- /dev/null +++ b/2019/src/day02.f90 @@ -0,0 +1,94 @@ +program day2 + implicit none + integer, parameter :: path_length = 100 + character(path_length) :: fname + integer :: n_arguments + integer, allocatable :: intcode(:) + integer :: n_codes + logical :: run_successful + + n_arguments = command_argument_count() + if (n_arguments .eq. 1) then + call get_command_argument(1, fname) + print *, "File: ", fname + else + print *, "Wrong number of arguments: ", n_arguments + stop + end if + + intcode = read_intcode(fname) + n_codes = size(intcode) + print "(4i5)", intcode + print *, "Running intcode" + call execute_intcode(intcode, n_codes, run_successful) + if (run_successful) then + print *, "Clean exit" + else + print *, "ERROR!" + end if + print * + print "(4i5)", intcode + print * + print *, "Value at position 0: ", intcode(0 + 1) + deallocate(intcode) + + contains + function read_intcode(fname) + integer, parameter :: fstr_len = 10000 + character(*), intent(in) :: fname + integer, allocatable :: read_intcode(:) + character(fstr_len) :: fstr + integer :: fstr_true_len + integer :: n_values = 0 + integer :: i + open(10, file=fname) + read(10, "(A)") fstr + close(10) + fstr_true_len = len_trim(fstr) + do i=1, fstr_true_len + if (fstr(i:i) .eq. ',') n_values = n_values + 1 + end do + allocate(read_intcode(0:n_values)) + read(fstr, *) read_intcode + end function read_intcode + + subroutine execute_intcode(intcode, icodelen, clean_exit) + integer, intent(inout) :: intcode(0:) + integer, intent(in) :: icodelen + logical, intent(out) :: clean_exit + integer, parameter :: max_iterations = 10000 + integer :: code_line + integer :: opcode + integer :: ipos_1 + integer :: ipos_2 + integer :: opos + integer :: op_result + !print "(4i5)", intcode + clean_exit = .false. + do code_line = 0, max_iterations + if (code_line * 4 .ge. icodelen) then + print *, "Overran intcode looking for opcode at line ", code_line + return + end if + opcode = intcode(code_line * 4) + if (opcode .eq. 99) then + print *, "Finished at line ", code_line + clean_exit = .true. + return + end if + ipos_1 = intcode(code_line * 4 + 1) + ipos_2 = intcode(code_line * 4 + 2) + opos = intcode(code_line * 4 + 3) + if (opcode .eq. 1) then + op_result = intcode(ipos_1) + intcode(ipos_2) + intcode(opos) = op_result + else if (opcode .eq. 2) then + op_result = intcode(ipos_1) * intcode(ipos_2) + intcode(opos) = op_result + else + print *, "Unknown opcode at line", code_line, " - ", opcode + return + end if + end do + end subroutine execute_intcode +end program day2 diff --git a/2019/src/day02b.f90 b/2019/src/day02b.f90 new file mode 100644 index 0000000..a97a5bb --- /dev/null +++ b/2019/src/day02b.f90 @@ -0,0 +1,118 @@ +program day2b + implicit none + integer, parameter :: path_length = 100 + integer, parameter :: param_max = 100 + integer, parameter :: target_output = 19690720 + character(path_length) :: fname + integer :: n_arguments + integer, allocatable :: intcode(:) + integer, allocatable :: test_intcode(:) + integer :: n_codes + logical :: run_successful, found_output + integer :: param1, param2, i + + n_arguments = command_argument_count() + if (n_arguments .eq. 1) then + call get_command_argument(1, fname) + print *, "File: ", fname + else + print *, "Wrong number of arguments: ", n_arguments + stop + end if + + intcode = read_intcode(fname) + allocate(test_intcode(1:n_codes)) + n_codes = size(intcode) + !print "(4i5)", intcode + found_output = .false. + do param1 = 0,param_max + do param2 = 0,param_max + do i=1,n_codes + test_intcode(i) = intcode(i) + end do + test_intcode(2) = param1 + test_intcode(3) = param2 + !print *, "Running intcode", param1, param2 + call execute_intcode(test_intcode, n_codes, run_successful) + if (.not. run_successful) then + print *, "ERROR!" + else if (test_intcode(1) .eq. target_output) then + found_output = .true. + exit + end if + end do + if (found_output) then + exit + end if + end do + if (found_output) then + print *, "Found combination of parameters to produce output:" + print *, param1, param2 + print *, "Combined: ", param1 * 100 + param2 + else + print *, "Failed to find input combination" + end if + deallocate(intcode) + deallocate(test_intcode) + + contains + function read_intcode(fname) + integer, parameter :: fstr_len = 10000 + character(*), intent(in) :: fname + integer, allocatable :: read_intcode(:) + character(fstr_len) :: fstr + integer :: fstr_true_len + integer :: n_values = 0 + integer :: i + open(10, file=fname) + read(10, "(A)") fstr + close(10) + fstr_true_len = len_trim(fstr) + do i=1, fstr_true_len + if (fstr(i:i) .eq. ',') n_values = n_values + 1 + end do + allocate(read_intcode(0:n_values)) + read(fstr, *) read_intcode + end function read_intcode + + subroutine execute_intcode(intcode, icodelen, clean_exit) + integer, intent(inout) :: intcode(0:) + integer, intent(in) :: icodelen + logical, intent(out) :: clean_exit + integer, parameter :: max_iterations = 10000 + integer :: code_line + integer :: opcode + integer :: ipos_1 + integer :: ipos_2 + integer :: opos + integer :: op_result + !print "(4i5)", intcode + clean_exit = .false. + do code_line = 0, max_iterations + if (code_line * 4 .ge. icodelen) then + print *, "Overran intcode looking for opcode at line ", code_line + return + end if + opcode = intcode(code_line * 4) + if (opcode .eq. 99) then + !print *, "Finished at line ", code_line + clean_exit = .true. + return + end if + ipos_1 = intcode(code_line * 4 + 1) + ipos_2 = intcode(code_line * 4 + 2) + opos = intcode(code_line * 4 + 3) + if (opcode .eq. 1) then + op_result = intcode(ipos_1) + intcode(ipos_2) + intcode(opos) = op_result + else if (opcode .eq. 2) then + op_result = intcode(ipos_1) * intcode(ipos_2) + intcode(opos) = op_result + else + print *, "Unknown opcode at line", code_line, " - ", opcode + return + end if + end do + end subroutine execute_intcode +end program day2b + diff --git a/2019/src/day2.f90 b/2019/src/day2.f90 deleted file mode 100644 index 00a1585..0000000 --- a/2019/src/day2.f90 +++ /dev/null @@ -1,44 +0,0 @@ -program day2 - implicit none - integer, parameter :: path_length = 100 - character(path_length) :: fname - integer :: n_arguments - integer, allocatable :: intcode(:) - integer :: n_codes - - n_arguments = command_argument_count() - if (n_arguments .eq. 1) then - call get_command_argument(1, fname) - print *, "File: ", fname - else - print *, "Wrong number of arguments: ", n_arguments - stop - end if - - intcode = read_intcode(fname) - n_codes = size(intcode) - print "(4i5)", intcode - print *, n_codes - deallocate(intcode) - - contains - function read_intcode(fname) - integer, parameter :: fstr_len = 10000 - character(*), intent(in) :: fname - integer, allocatable :: read_intcode(:) - character(fstr_len) :: fstr - integer :: fstr_true_len - integer :: n_values = 0 - integer :: i - open(10, file=fname) - read(10, "(A)") fstr - close(10) - fstr_true_len = len_trim(fstr) - do i=1, fstr_true_len - if (fstr(i:i) .eq. ',') n_values = n_values + 1 - end do - allocate(read_intcode(0:n_values)) - print *, n_values - read(fstr, *) read_intcode - end function read_intcode -end program day2