Example #1
0
def astar(state, heuristic):
	queue = []
	# prevStateDict[state] = (previous state, move to get there, g)
	prevStateDict = {}
	prevStateDict[state] = (None, None, 0)
	heappush(queue, (heuristic(state), state)) 
	
	while queue:
		f, state = heappop(queue) # f is total astar cost
		
		if state == puzzle8.solution():
			prevState = prevStateDict[state]
			path = []
			#print("backtracing")
			while prevState[0]:
				path = [prevState[1]] + path
				prevState = prevStateDict[prevState[0]]
			return path

		g = f - heuristic(state) # g is cost in moves to get to current state
		neighbors = puzzle8.neighbors(puzzle8.blankSquare(state))

		for neighbor in neighbors:
			newState = puzzle8.moveBlank(state, neighbor)
			
			if newState not in prevStateDict:
				prevStateDict[newState] = (state, neighbor, g+1)
			else:
				if prevStateDict[newState][2] > g+1:
					# if we just found a cheaper path to newState, override prevStateDict
					prevStateDict[newState] = (state, neighbor, g+1)


			f = g + 1 + heuristic(newState)
			heappush(queue, (f, newState))
Example #2
0
def manhattanDistance(state):
	manhattanDistance = 0
	for i in range(9):
		tile = puzzle8.getTile(state, i)
		j = xyposition(puzzle8.solution(), tile)
		manhattanDistance += math.fabs(puzzle8.xylocation(i)[0] - puzzle8.xylocation(j)[0])
		manhattanDistance += math.fabs(puzzle8.xylocation(i)[1] - puzzle8.xylocation(j)[1])
	return manhattanDistance
Example #3
0
def numWrongTiles(state):
	'''gives number of tiles differing between given state and solution state'''
	numWrong = 0
	for i in range(0,9):
		if puzzle8.getTile(state,i) != 0 and \
			puzzle8.getTile(state,i) != puzzle8.getTile(puzzle8.solution(),i):
			numWrong += 1
	return numWrong
Example #4
0
    def testItdeep(self):
        self.assertEqual(search.itdeep(puzzle8.solution()),[])
        self.assertEqual(len(search.itdeep(puzzle8.randomState(1))),1)
        testPuzzle = puzzle8.state([1,2,0,8,6,3,7,5,4])
        self.assertEqual(search.itdeep(testPuzzle),[5,8,7,4])

        random.seed(12345)
        randomMoves = 32
        testPuzzle2 = puzzle8.randomState(randomMoves)
        puzzle8.display(testPuzzle2)
        solnPath = search.itdeep(testPuzzle2)
        self.assertLessEqual(len(solnPath),randomMoves)
Example #5
0
def astar(initial_state, heuristic):
	fringe = Queue.PriorityQueue()
	fringe.put((0+heuristic(initial_state), initial_state, []))
	while True:
		h, state, path = fringe.get()
		if state == puzzle8.solution():
			return path
		zero_position = xyposition(state, 0)
		for neighbor in puzzle8.neighbors(zero_position):
			next_state = puzzle8.moveBlank(state, neighbor)
			# note: we add neighbor/10. to make sure that neighbors are taken out in the appropriate order
			fringe.put((len(path)+1+heuristic(next_state)+neighbor/10., next_state, path+[[zero_position, neighbor]]))
Example #6
0
def manhattanDistance(state):
	'''gives sum of manhattan distance of all tiles from their
	respective places in the solution state.'''
	dist = 0
	for i in range(0,9):
		tile = puzzle8.getTile(state, i)
		if tile == 0:
			continue
		loc1 = puzzle8.xylocation(i)
		loc2 = puzzle8.xylocation(findTile(puzzle8.solution(), tile))
		dist += abs(loc1[0]-loc2[0]) + abs(loc1[1]-loc2[1])
	return dist
Example #7
0
def depthLimitedDFS(initial_state, depth):
	fringe = Queue.LifoQueue()
	fringe.put((initial_state, []))
	while not fringe.empty():
		state, path = fringe.get()
		if state == puzzle8.solution():
			return path
		if len(path) == depth:
			continue
		zero_position = xyposition(state, 0)
		for neighbor in puzzle8.neighbors(zero_position):
			next_state = puzzle8.moveBlank(state, neighbor)
			fringe.put((next_state, path+[[zero_position, neighbor]]))
	return False
Example #8
0
def recdepthLimitedDFS(state, height):
	# if found, return
	if state == puzzle8.solution():
		return []
	# if we're at the bottom, return
	if height == 0:
		return False
	# find 0 and iterate over neighbors
	zero_position = xyposition(state, 0)
	for neighbor in puzzle8.neighbors(zero_position):
		next_result = depthLimitedDFS(puzzle8.moveBlank(state, neighbor), height-1)
		# if next_result is a list, we've found a solution
		if isinstance(next_result, list):
			return [[zero_position, neighbor]] + next_result
	# we're out of things to do
	return False
Example #9
0
def recurDeep(state, depthRemaining):
	'''searches for a path with depth given.
	   if not found, returns [-1].'''
	if state == puzzle8.solution():
		return []
	if depthRemaining <= 0:
		return [-1]

	neighbors = puzzle8.neighbors(puzzle8.blankSquare(state))
	depthRemaining -= 1
	for neighbor in neighbors:
		newState = puzzle8.moveBlank(state, neighbor)
		possiblePath = recurDeep(newState, depthRemaining)
		if -1 not in possiblePath:
			path = [neighbor] + possiblePath
			return path
	return [-1]
Example #10
0
 def testManhattanDistance(self):
     self.assertEqual(search.manhattanDistance(puzzle8.solution()),0)
     self.assertEqual(search.manhattanDistance(puzzle8.randomState(1)),1)
     self.assertEqual(search.manhattanDistance(self.offTwoPuzzle),16)
Example #11
0
 def testNumWrongTiles(self):
     self.assertEqual(search.numWrongTiles(puzzle8.solution()),0)
     self.assertEqual(search.numWrongTiles(puzzle8.randomState(1)),1)
     self.assertEqual(search.numWrongTiles(self.offTwoPuzzle),8)
Example #12
0
def numWrongTiles(state):
	numWrongTiles = 0
	for i in range(9):
		if puzzle8.getTile(state, i) != puzzle8.getTile(puzzle8.solution(), i):
			numWrongTiles += 1
	return numWrongTiles