I used recursion again for the Part 2 scan along the line of sight. Really liking how it simplifies this sort of repetitive stuff.
I could also reduce code lines by combining P1 and P2 with a conditional section on part number, but can't be bothered. And for execution time, this way will be (marginally) faster anyway.
******************************
def TestSeatP1 (row, col):
global seats
num_col = len (seats
num_row = len (seats)
#set up matrix for valid test
test_valid = [[row>0 and col>0,row>0, row>0 and col<num_col - 1],
[col>0,False,col<num_col-1],
[row<num_row-1 and col>0,row<num_row-1,col<num_col-1 and row<num_row-1]]
#examine surrounding seats
count_occupied = 0
for rs in range (3):
for cs in range (3):
if test_valid[rs][cs]:
seat_val = seats[row+rs-1][col+cs-1]
if seat_val == "#":
count_occupied += 1
return (count_occupied)
def ScanP2 (row, col, rcnt, ccnt):
#set up matrix for valid test
num_col = len (seats
num_row = len (seats)
test_valid = [[row>0 and col>0,row>0, row>0 and col<num_col - 1],
[col>0,False,col<num_col-1],
[row<num_row-1 and col>0,row<num_row-1,col<num_col-1 and row<num_row-1]]
if test_valid [rcnt][ccnt]:
seat_val = seats[row+rcnt-1][col+ccnt-1]
if seat_val == ".":
return ScanP2 (row+rcnt-1,col+ccnt-1,rcnt, ccnt)
else:
return seat_val
else:
return "E"
def TestSeatP2 (row, col):
global seats
num_col = len (seats
num_row = len (seats)
#examine surrounding seats
count_occupied = 0
for rs in range (3):
for cs in range (3):
if ScanP2 (row, col, rs, cs) == "#":
count_occupied += 1
return (count_occupied)
# start get data
input_file = open("11Input.txt", "r")
#data = [(line.strip()).split() for line in input_file]
seats = [line.strip() for line in input_file]
input_file.close()
#take a copy for part 2
original_seats = seats.copy()
# part 1
changed = True
iterations = 0
seats_new = []
while changed:
print ("part 1", iterations)
# for index, row in enumerate (seats):
# if index<10:
# print (row)
num_changes = 0
num_occupied = 0
seats_new = seats.copy()
for row in range (len (seats)):
for col in range (len(seats[0])):
now = seats [row][col]
occupied = TestSeatP1 (row,col)
if now == "#" and occupied >= 4:
new = "L"
num_changes+= 1
elif now == "L" and occupied == 0:
new = "#"
num_changes += 1
else:
new = now
seats_new [row] = seats_new[row][:col]+ new + seats_new [row][col+1:]
seats = seats_new.copy()
if num_changes == 0:
changed = False
else:
iterations += 1
for row in range (len (seats)):
for col in range (len(seats[0])):
now = seats [row][col]
if now == "#":num_occupied += 1
part1Ans = num_occupied
part1Iterations = iterations
# part 2
seats = original_seats.copy ()
changed = True
iterations = 0
seats_new = []
while changed:
print ("part 2", iterations)
# for index, row in enumerate (seats):
# if index<10:
# print (row)
num_changes = 0
num_occupied = 0
seats_new = seats.copy()
for row in range (len (seats)):
for col in range (len(seats[0])):
now = seats [row][col]
occupied = TestSeatP2 (row,col)
if now == "#" and occupied >= 5:
new = "L"
num_changes+= 1
elif now == "L" and occupied == 0:
new = "#"
num_changes += 1
else:
new = now
seats_new [row] = seats_new[row][:col]+ new + seats_new [row][col+1:]
seats = seats_new.copy()
if num_changes == 0:
changed = False
else:
iterations += 1
for row in range (len (seats)):
for col in range (len(seats[0])):
now = seats [row][col]
if now == "#":num_occupied += 1
part2Ans = num_occupied
part2Iterations = iterations
print ("Part 1: No iterations ", part1Iterations,"Number occupied: ", part1Ans)
print ("Part 2: No iterations ", part2Iterations,"Number occupied: ", part2Ans)