コード例 #1
0
    def _general_circle_elimination(self, model: grb.Model):
        edges_solution = model.cbGetSolution(self.edges)
        used_edges = grb.tupledict({key: edges_solution[key] for key in edges_solution if not math.isclose(0, edges_solution[key], abs_tol=10**-5)})
        for edge in used_edges:
            if used_edges[edge] < 0.7:
                print("Found an edge with value less than 0.7")
        
        self._check_for_cycle(used_edges, model)
        return
        # Turn used_edges into a dependency graph
        dep_graph = self._get_dep_graph(used_edges)

        try:
            calculate_order(dep_graph, calculate_circle_dep=True)
        except CircularDependencyException as dep_exception:
            self._add_cycle_constr(dep_exception.circle_nodes, model)
        # For now we try to ignore this disconnected graphs
        except DisconnectedDependencyGraphException as disc_exception:
            cycle = calculate_cycle(disc_exception.disconnected_nodes)
            self._add_cycle_constr(cycle, model)
コード例 #2
0
    def solve(self, graph: Graph, **kwargs):
        self.time_limit = kwargs.pop("time_limit", self.max_time)
        self.upper_bound = kwargs.pop("upper_bound", None)
        self.relax_solver.build_model(graph)
        self.relax_solver.set_output(False)
        self.abs_graph = self.relax_solver.abstract_graph
        self.edge_vars = self.relax_solver.edges
        self.max_edges = 0
        for v_i in range(len(graph.vertices)):
            # Constraint over all vertices: least 2k-1 connections between incident edges
            incident_vertices = [
                i for i in range(self.abs_graph.vert_amount)
                if np.intersect1d(self.abs_graph.vertices[i], v_i).size > 0
            ]
            self.max_edges += (len(incident_vertices) - 1)

        self.solve_time_start = time.time()
        self.lock = asyncio.Lock()
        asyncio.get_event_loop().run_until_complete(
            self._inner_solve(self.abs_graph, {}, 0, 0, {}))

        status = 'OPTIMAL'
        if self.time_limit and time.time(
        ) - self.solve_time_start > self.time_limit:
            status = 'TIME_LIMIT'
        returned_order = None
        self.upper_bound = None
        if self.upper_bound_sol:
            dep_graph = self._get_dep_graph(self.upper_bound_sol)
            order = calculate_order(dep_graph, calculate_circle_dep=True)
            returned_order = [tuple(self.abs_graph.vertices[i]) for i in order]
        sol = AngularGraphSolution(graph,
                                   time.time() - self.solve_time_start,
                                   solution_type=self.solution_type,
                                   solver=self.__class__.__name__,
                                   is_optimal=status == "OPTIMAL",
                                   order=returned_order)

        self.upper_bound_sol = None
        return sol
コード例 #3
0
    def solve(self, graph: Graph, **kwargs):
        error_message = None
        returned_order = None
        is_optimal = False
        runtime = 0
        try:
            self.build_model(graph)
            if "time_limit" in kwargs:            
                self.model.setParam("TimeLimit", kwargs.pop("time_limit"))
            self.add_start_solution(graph, kwargs.pop("start_solution", None))
            self._add_callbacks(kwargs.pop("callbacks", None))
            if kwargs.pop("relax", False):
                old_edges = self.edges
                used_edges = None
                rel_model = self.model.relax()
                keys, self.edges = grb.multidict({key: rel_model.getVarByName(self.edges[key].VarName) for key in self.edges})
                rel_model.optimize(callback_rerouter)
                runtime = self.model.Runtime
                
            else:
                circle_found = True
                max_runtime = self.params["TimeLimit"]
                while(circle_found and max_runtime > 0):
                    self.model.optimize(callback_rerouter)
                    max_runtime -= self.model.Runtime
                    runtime = abs(self.params["TimeLimit"] - max_runtime)
                    try:
                        used_edges = grb.tupledict({key: self.edges[key] for key in self.edges if not math.isclose(0, self.edges[key].x, abs_tol=10**-6)})
                        circle_found = self._check_for_cycle(used_edges, self.model, lazy=False)
                        if circle_found and max_runtime > 0:
                            self.model.setParam("TimeLimit", max_runtime)
                    except AttributeError as e:
                        # Can happen if no solution was found in the time limit
                        # If not, raise error
                        if runtime < self.params["TimeLimit"]:
                            raise e
                    

            is_optimal = self.model.Status == grb.GRB.OPTIMAL
            if is_debug_env():
                local_subtours = 0
                for circle in self.found_circles:
                    verts = [key[1] for key in circle]
                    for v_i in self.v_incident_edges:
                        if self.v_incident_edges[v_i].issuperset(verts):
                            local_subtours += 1
                            break
                print("Overall subtours:", len(self.found_circles), "local subtours:", local_subtours,\
                    "in percent:", local_subtours*100/len(self.found_circles))
            
            try:
                used_edges = {key: self.edges[key] for key in self.edges if not math.isclose(0, self.edges[key].x, abs_tol=10**-6)}
                dep_graph = self._get_dep_graph(used_edges)
                order = calculate_order(dep_graph, calculate_circle_dep=True)
                returned_order = [tuple(self.abstract_graph.vertices[i]) for i in order]
            except (CircularDependencyException, AttributeError) as e:
                # If we have a circular dependency after the time limit we just didnt managed to get a feasable solution in time
                # Else something went wrong and the error should be raised
                if runtime < self.params["TimeLimit"]:
                    raise e
        except Exception as e:
            error_message = str(e)
            if is_debug_env():
                raise e
        #times = calculate_times(returned_order, self.graph)
        sol = AngularGraphSolution(self.graph,
                                    runtime,
                                    solution_type=self.solution_type,
                                    solver=self.__class__.__name__,
                                    is_optimal=is_optimal,
                                    order=returned_order,
                                    error_message=error_message)
        return sol
コード例 #4
0
ファイル: s_n_2_solver.py プロジェクト: ahillbs/ma-ahill
 def _calculate_order(self,
                      dependency_graph: DependencyGraph) -> SolveOrder:
     return calculate_order(dependency_graph)