예제 #1
0
    def brute_force_solution(graph,
                             current_vertex_id=1,
                             reduce_ram_usage=False):
        # Generate route log path
        if reduce_ram_usage:
            route_log_path =os.getcwd() + os.path.sep + ".." + os.path.sep + "logs" + os.path.sep + \
                            "RouteLog_{0}_{1}".format(len(graph.vertices), str(time.time())[:9])

        # Recursive function for trying all adjacent vertices.
        def try_all_open_routes_from_current_route(route,
                                                   reduce_ram_usage=False):
            # Initialize Routes to keep track of all attempted routes.
            routes = np.array([])
            # Start at the current vertex id location
            current_vertex = route.graph.vertices[current_vertex_id]

            # For each adjacent vertex that has not been visited
            for adjacent_vertex in current_vertex.get_unvisited_adjacent_vertex_ids(
            ):
                # copy the route so far
                new_route = deepcopy(route)
                # goto the current adjacent_vertex
                new_route.goto(adjacent_vertex.vertex_id)

                # if all vertices have been visisted
                if new_route.graph.finished():
                    # goto the current vertex id
                    new_route.goto(current_vertex_id)

                    if reduce_ram_usage:
                        # Log finished route to hard disk
                        FileHandler.log_route(new_route, route_log_path)
                        # Delete from RAM
                        del new_route
                    else:
                        # append the route to the list of completed routes
                        routes = np.concatenate((routes, new_route), axis=None)
                else:  # if not,
                    if reduce_ram_usage:
                        try_all_open_routes_from_current_route(
                            new_route, reduce_ram_usage)
                    else:
                        # Recall the recursive function using the updated route.
                        routes = np.concatenate((
                            routes,
                            try_all_open_routes_from_current_route(new_route)),
                                                axis=None)

            # After all adjacent vertices have been visisted recursively, return the list of routes
            return routes

        # Initialize the route
        route = Route(list([]), graph)
        # goto the current vertex id
        route.goto(current_vertex_id)

        # Initialize a list of routes
        routes = np.array([])

        # Recursively try all open routes from the current route, advancing when possible.
        routes = np.concatenate(
            (routes,
             try_all_open_routes_from_current_route(
                 route, reduce_ram_usage=reduce_ram_usage)),
            axis=None)

        if reduce_ram_usage:
            del routes
            # Sift file located at route_log_path for the shortest route
            return FileHandler.find_minimum_route(route_log_path)
        else:
            # Identify the route with minimum distance traveled
            return min(routes)
예제 #2
0
    class GreedyAlgorithm(object):
        def __init__(self, graph, starting_vertex_id=1, reset_heuristic=False):
            self.route = Route(graph)
            self.starting_vertex_id = starting_vertex_id
            self.route.goto(
                self.route.graph.get_vertex_by_id(starting_vertex_id))
            self.done = False
            self.attempted_starting_vertex_ids = list([starting_vertex_id])
            self.remaining_starting_vertex_ids = self.get_remaining_starting_vertex_ids(
            )
            self.reset_heuristic = reset_heuristic
            self.crosses = 0

        def __eq__(self, other):
            return self.route.distance_traveled == other.route.distance_traveled

        def __lt__(self, other):
            return self.route.distance_traveled < other.route.distance_traveled

        def __le__(self, other):
            return self.route.distance_traveled <= other.route.distance_traveled

        def __gt__(self, other):
            return self.route.distance_traveled > other.route.distance_traveled

        def __ge__(self, other):
            return self.route.distance_traveled >= other.route.distance_traveled

        def __str__(self):
            string = "Starting vertex id: " + str(
                self.starting_vertex_id) + "\n"

            string += "Route: " + str(self.route) + "\n"

            string += "reset_heuristic: " + str(self.reset_heuristic) + "\n"

            string += "Crosses: " + str(self.crosses)

            return string

        def complete(self):
            while not self.done:
                self.step_forward()

            return self.route

        def step_forward(self):
            next_vertex, closest_item_next_to_vertex = self.choose_next_vertex(
            )
            self.route.lasso(next_vertex, closest_item_next_to_vertex)

            if len(self.route.vertices) > len(self.route.graph.vertices):
                self.done = True

        def step_backward(self):
            if len(self.route.vertices) > 0:
                self.route.walk_back()
                self.attempted_starting_vertex_ids.pop()
                self.remaining_starting_vertex_ids = self.get_remaining_starting_vertex_ids(
                )

                if self.done:
                    self.done = False

        def choose_next_vertex(self):
            closest_item_next_to_closest_vertex = None
            r_type_of_closest_item = None
            closest_vertex = None
            closest_distance = None

            for vertex in self.route.get_unvisited_vertices():
                closest_item_next_to_vertex, item_distance = self.route.get_shortest_distance_to_route(
                    vertex)

                if closest_vertex is None:
                    closest_vertex = vertex
                    closest_distance = item_distance
                    closest_item_next_to_closest_vertex = closest_item_next_to_vertex
                else:
                    if item_distance < closest_distance:
                        closest_distance = item_distance
                        closest_vertex = vertex
                        closest_item_next_to_closest_vertex = closest_item_next_to_vertex

            if len(self.route.get_unvisited_vertices()) == 0:
                return self.route.vertices[0], self.route.vertices[1]
            else:
                return closest_vertex, closest_item_next_to_closest_vertex

        def get_remaining_starting_vertex_ids(self):
            return [
                vertex_id for vertex_id in list(
                    range(1,
                          len(self.route.graph.vertices) + 1))
                if vertex_id not in self.attempted_starting_vertex_ids
            ]