def createStatesManhatan(current_state):
	children = []
	zeroPosition = current_state.zeroIndex()
	mtrx = current_state.getMatrix()
	# Up
	newArray = up(current_state.getMatrix(), zeroPosition)
	if newArray is not None:
		newState = State(newArray, depth = current_state.depth +1, parent = current_state)
		newState.f = manhathanDistance(newArray)
		children.append(newState)
	# Down
	newArray = down(current_state.getMatrix(), zeroPosition)
	if newArray is not None:
		newState = State(newArray, depth = current_state.depth +1, parent = current_state)
		newState.f = manhathanDistance(newArray)
		children.append(newState)
	# Left
	newArray = left(current_state.getMatrix(), zeroPosition)
	if newArray is not None:
		newState = State(newArray, depth = current_state.depth +1, parent = current_state)
		newState.f = manhathanDistance(newArray)
		children.append(newState)
	# Right
	newArray = right(current_state.getMatrix(), zeroPosition)
	if newArray is not None:
		newState =	 State(newArray, depth = current_state.depth +1, parent = current_state)
		newState.f = manhathanDistance(newArray)
		children.append(newState)

	return children
def hc_Steepest(matrix):
	# Set up inital condition.
	currentState = State(matrix)
	currentState.f = manhathanDistance(matrix)
	nextState = State(matrix)
	nextState.f = copy(currentState.f)
	statesCount = 1

	while True:
		children = createStatesManhatan(currentState)
		for child in children:
			statesCount +=1
			if child.f < nextState.f:
				nextState = child
		if nextState.f >= currentState.f:
			if nextState.isGoal():
				return "Goal", nextState, statesCount
			else:
				return 'Local Maxima', nextState, statesCount
		currentState = copy(nextState)
	return None
def hc_RandomRestart(matrix, count):
	# Set up inital condition.
	# Ask for all requiered input.
	currentState = State(copy(matrix))
	currentState.f = manhathanDistance(copy(matrix))
	nextState = State(copy(matrix))
	nextState.f = copy(currentState.f)
	statesCount = count

	while True:
		children = createStatesManhatan(currentState)
		for child in children:
			statesCount +=1
			if child.f < nextState.f:
				nextState = child
		if nextState.f >= currentState.f:
			if nextState.isGoal():
				return "Goal", nextState, statesCount
			else:
				return hc_RandomRestart(createMovesRandomRestart(copy(matrix)), statesCount)
		currentState = copy(nextState)
	return None