def getNextJump(self, center, direction): print(" getNextJump : Center", center, direction) center_boundary_pos = self.blist.get_next_closed_boundary_pos(center, direction) if Direction.get_direction(center,self.endPos) == direction: if self.distance(center, center_boundary_pos, direction) > self.distance(center, self.endPos, direction): print(" returning endPos") return self.endPos left_neighbour = Direction.get_neighbour(center, self.leftDict[direction]) left_open_pos = self.blist.get_next_open_boundary_pos(left_neighbour, direction) print(" Left", left_neighbour, left_open_pos) if left_open_pos != None: if self.distance(center, center_boundary_pos, direction) > self.distance(left_neighbour, left_open_pos, direction): njump = Direction.get_position(center, direction, self.distance(left_neighbour, left_open_pos, direction)) print(" returning ", njump) return njump right_neighbour = Direction.get_neighbour(center, self.rightDict[direction]) right_open_pos = self.blist.get_next_open_boundary_pos(right_neighbour, direction) print(" Right", right_neighbour, right_open_pos) if right_open_pos != None: if self.distance(center, center_boundary_pos, direction) > self.distance(right_neighbour, right_open_pos, direction): njump = Direction.get_position(center, direction, self.distance(right_neighbour, right_open_pos, direction)) print(" returning ", njump) return njump print(" returning None - no jump") return None
def jump(self, lastPos, direction): curPos = Direction.get_neighbour(lastPos, direction) print("Jump: ", lastPos, curPos, direction) if not self.is_passable(curPos) : return None if curPos == self.endPos: return curPos has_forced= self.has_forced(curPos, direction) if has_forced: return curPos if direction in Direction.diagonals: first, second = direction while (True): for cardinal in (first, second): nextPos = self.getNextJump(curPos, cardinal) if nextPos != None: return curPos if self.is_reachable(curPos, direction): curPos = Direction.get_neighbour(curPos, direction) else: break return None else: nextPos = self.getNextJump(curPos, direction) return nextPos
def check_forced(self, pos, blockdir, forcedir): bPos = Direction.get_neighbour(pos, blockdir) blocked = not self.is_passable(bPos) fPos = Direction.get_neighbour(pos, forcedir) forced = self.is_passable(fPos) return blocked and forced
def get_forced(self, pos, dirn): pm = self.forced_params[dirn] #b_left = pm[0], f_left = pm[1], b_right = pm[2], f_right = pm[3] forced = {} if self.check_forced(pos, pm[0], pm[1]): forced[pm[1]] = Direction.get_neighbour(pos, pm[1]) if self.check_forced(pos, pm[2], pm[3]): forced[pm[3]] = Direction.get_neighbour(pos, pm[3]) return forced
def get_forced(self, pos, dirn): pm = self.forced_params[dirn] #b_left = pm[0], f_left = pm[1], b_right = pm[2], f_right = pm[3] forced = {} if self.check_forced(pos, pm[0], pm[1]): forced[pm[1]] = Direction.get_neighbour(pos, pm[1]) if self.check_forced(pos, pm[2], pm[3]): forced[pm[3]]= Direction.get_neighbour(pos, pm[3]) return forced
def is_reachable(self, pos, dirn): npos = Direction.get_neighbour(pos, dirn) in_bounds = self.in_bounds(npos) is_open = False if in_bounds: is_open = self.is_passable(npos) if dirn in Direction.diagonals: d1, d2 = dirn p1 = Direction.get_neighbour(pos, d1) p2 = Direction.get_neighbour(pos, d2) is_open = is_open and (self.is_passable(p1) and self.is_passable(p2) ) return in_bounds and is_open
def testGetNeighbours(self): '''check that get_neighbours gives back the right neighbour coordinates''' pos = (3,3) expected = [(2,2), (2,3), (2,4), (3,2), (3,4), (4,2), (4,3), (4,4)] actual = sorted(Direction.get_neighbours(pos).values()) self.assertEqual(actual, expected)
def __init__(self, selfPos, parent, endPos, grid, cutting=True): self.pos = selfPos self.endPos = endPos self.parent = parent self.grid = grid if parent == None: self.cost = 0.0 self.dirn = Direction.get_direction(self.pos, self.pos) else: self.cost = parent.get_cost() + parent.calc_cost(selfPos) self.dirn = Direction.get_direction(self.parent.get_pos(), self.pos) self.prox = self.calc_cost(endPos)
def testGetNeighbours(self): '''check that get_neighbours gives back the right neighbour coordinates''' pos = (3, 3) expected = [(2, 2), (2, 3), (2, 4), (3, 2), (3, 4), (4, 2), (4, 3), (4, 4)] actual = sorted(Direction.get_neighbours(pos).values()) self.assertEqual(actual, expected)
def prune(self, pos, dirn): #first - deal with starting node (no direction) if dirn == "O": return Direction.get_neighbours(pos) #otherwise generate the pruned neighbours pruned = {} #get natural neighbours for nat in self.naturals[dirn]: pruned[nat] = Direction.get_neighbour(pos, nat) #get forced neighbours forced = self.get_forced(pos, dirn) for fn in forced: pruned[fn] = forced[fn] return pruned
def get_forced(self, pos, dirn): pm = self.forced_params[dirn] #b_left = pm[0], f_left_cardinal = pm[1], f_left_diagonal = pm[2], #b_right = pm[3], f_right_cardinal = pm[4], f_right_diagonal = pm[5], forced = {} if len(pm) > 0: if self.check_forced(pos, pm[0], pm[1]): forced[pm[1]] = Direction.get_neighbour(pos, pm[1]) if self.check_forced(pos, pm[0], pm[2]): forced[pm[2]] = Direction.get_neighbour(pos, pm[2]) if self.check_forced(pos, pm[3], pm[4]): forced[pm[4]]= Direction.get_neighbour(pos, pm[4]) if self.check_forced(pos, pm[3], pm[5]): forced[pm[5]]= Direction.get_neighbour(pos, pm[5]) return forced
def testGetDirection(self): '''check that get_direction gives back the right compass direction''' fromPos = (3,3) expected = {(3,2):"N", (4,2):"NE", (4,3):"E", (4,4):"SE", (3,4):"S", (2,4):"SW", (2,3):"W", (2,2):"NW"} for toPos in expected.keys(): actual = Direction.get_direction(fromPos, toPos) self.assertEqual(actual, expected[toPos], "Expected {}, got {})".format(expected[toPos], actual))
def testGetNeighbour(self): '''check that get_neighbour gives back the right coordinates given a compass direction''' fromPos = (3,3) expected = {"N":(3,2), "NE":(4,2), "E":(4,3), "SE":(4,4), "S":(3,4), "SW":(2,4), "W":(2,3), "NW":(2,2)} for dirn in expected.keys(): actual = Direction.get_neighbour(fromPos, dirn) self.assertEqual(actual, expected[dirn], "Expected {}, got {})".format(expected[dirn], actual))
def testGetDirection(self): '''check that get_direction gives back the right compass direction''' fromPos = (3, 3) expected = { (3, 2): "N", (4, 2): "NE", (4, 3): "E", (4, 4): "SE", (3, 4): "S", (2, 4): "SW", (2, 3): "W", (2, 2): "NW" } for toPos in expected.keys(): actual = Direction.get_direction(fromPos, toPos) self.assertEqual( actual, expected[toPos], "Expected {}, got {})".format(expected[toPos], actual))
def testGetNeighbour(self): '''check that get_neighbour gives back the right coordinates given a compass direction''' fromPos = (3, 3) expected = { "N": (3, 2), "NE": (4, 2), "E": (4, 3), "SE": (4, 4), "S": (3, 4), "SW": (2, 4), "W": (2, 3), "NW": (2, 2) } for dirn in expected.keys(): actual = Direction.get_neighbour(fromPos, dirn) self.assertEqual( actual, expected[dirn], "Expected {}, got {})".format(expected[dirn], actual))
def jump(self, lastPos, direction): curPos = Direction.get_neighbour(lastPos, direction) if not self.is_passable(curPos) : return None if curPos == self.endPos: return curPos has_forced= self.has_forced(curPos, direction) if has_forced: return curPos if direction in Direction.diagonals: for cardinal in direction: nextPos = self.jump(curPos, cardinal) if nextPos != None: return curPos return self.jump(curPos, direction)
def jump(self, lastPos, direction): curPos = Direction.get_neighbour(lastPos, direction) if not self.is_passable(curPos): return None if curPos == self.endPos: return curPos has_forced = self.has_forced(curPos, direction) if has_forced: return curPos if direction in Direction.diagonals: for cardinal in direction: nextPos = self.jump(curPos, cardinal) if nextPos != None: return curPos return self.jump(curPos, direction)
[1, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 0], [0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0], [0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0]] startPos = (0, 10) endPos = (11, 9) print(startPos, endPos) jumps = PathFinder.findPath(startPos, endPos, grid) print(jumps, '\n') path = [] for j in range(len(jumps) - 1): pos = jumps[j] target = jumps[j + 1] dirn = Direction.get_direction(pos, target) while pos != target: path.append(pos) pos = Direction.get_neighbour(pos, dirn) grid[startPos[1]][startPos[0]] = "S" for p in path: grid[p[1]][p[0]] = '*' for j in jumps: grid[j[1]][j[0]] = 'j' grid[endPos[1]][endPos[0]] = "E" print(Grid.string(grid))