Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- """Advent of Code 2016 day 1 solutions"""
- import re
- NORTH = (0, 1)
- EXAMPLE_STEPS = [('R', 8), ('R', 4), ('R', 4), ('R', 8)]
- def turn(direction, side):
- """
- Turns direction vector left or right by 90 degrees
- >>> turn(NORTH, 'L')
- (-1, 0)
- >>> turn(NORTH, 'R')
- (1, 0)
- """
- d_x, d_y = direction
- if side == 'L':
- return -d_y, d_x
- elif side == 'R':
- return d_y, -d_x
- else:
- raise ValueError('Invalid side: %s' % side)
- def teleport(steps):
- """
- The last coordinates of Santa
- >>> teleport(EXAMPLE_STEPS)
- (4, 4)
- """
- coords = (0, 0)
- direction = NORTH
- for (side, distance) in steps:
- direction = turn(direction, side)
- c_x, c_y = coords
- d_x, d_y = direction
- coords = (c_x + d_x * distance, c_y + d_y * distance)
- return coords
- def walk(steps):
- """
- The path of Santa
- >>> steps = [('R', 2), ('L', 2)]
- >>> list(walk(steps))
- [(1, 0), (2, 0), (2, 1), (2, 2)]
- """
- coords = (0, 0)
- direction = NORTH
- for (side, distance) in steps:
- direction = turn(direction, side)
- for _ in range(distance):
- c_x, c_y = coords
- d_x, d_y = direction
- coords = (c_x + d_x, c_y + d_y)
- yield coords
- def find_first_duplicate(iteratable):
- """
- Finds the first duplicate in iteratable
- >>> find_first_duplicate([0, 1, 2, 1, 2])
- 1
- """
- visited = set()
- for elem in iteratable:
- if elem in visited:
- return elem
- visited.add(elem)
- def manhattan_distance_from_origin(coords):
- """
- Manhattan's distance to (0, 0)
- >>> manhattan_distance_from_origin((4, -4))
- 8
- """
- c_x, c_y = coords
- return abs(c_x) + abs(c_y)
- def main():
- """Main function"""
- with open('input.txt', 'r') as handle:
- pattern = r'([RL])(\d+)'
- matches = re.findall(pattern, handle.read())
- steps = [(side, int(distance)) for (side, distance) in matches]
- part1 = teleport(steps)
- print('Part 1:', manhattan_distance_from_origin(part1))
- path = walk(steps)
- part2 = find_first_duplicate(path)
- print('Part 2:', manhattan_distance_from_origin(part2))
- if __name__ == '__main__':
- main()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement