Spaces:
Configuration error
Configuration error
File size: 3,417 Bytes
3dc2617 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 |
import logging
import numpy as np
import pandas as pd
from ortools.constraint_solver import routing_enums_pb2, pywrapcp
logger = logging.getLogger("Orbix")
class OrbitalPathOptimizer:
"""
Optimiza la ruta orbital utilizando OR-Tools aplicando un TSP sobre puntos de desechos.
A partir de la posici贸n actual del sat茅lite y las coordenadas (x, y, z) de cada desecho,
se obtiene la ruta 贸ptima que minimiza la distancia total a recorrer.
"""
def optimize_route(self, satellite_state: dict, debris_data: pd.DataFrame):
"""
Optimiza la ruta a partir del estado del sat茅lite y datos de desechos.
Se espera que debris_data tenga columnas 'debris_id', 'x', 'y', 'z'.
satellite_state debe tener una llave 'position' con una tupla (x, y, z).
Retorna una lista de tuplas (debris_id, x, y, z) en el orden 贸ptimo.
"""
if debris_data.empty or 'position' not in satellite_state:
logger.error("Datos de desechos vac铆os o estado del sat茅lite sin 'position'.")
return []
# Posici贸n del sat茅lite (punto de partida)
start = np.array(satellite_state['position'])
# Extraer posiciones (x, y, z) de cada desecho
points = debris_data[['x','y','z']].to_numpy()
# Crear matriz de todos los puntos (incluye el punto de inicio)
all_points = np.concatenate(([start], points), axis=0)
num_points = len(all_points)
# Construir la matriz de distancias
distance_matrix = np.zeros((num_points, num_points))
for i in range(num_points):
for j in range(num_points):
if i != j:
distance_matrix[i][j] = np.linalg.norm(all_points[i] - all_points[j])
else:
distance_matrix[i][j] = 0
# Configurar el modelo de OR-Tools para TSP (sin retorno al punto de inicio)
manager = pywrapcp.RoutingIndexManager(num_points, 1, 0)
routing = pywrapcp.RoutingModel(manager)
def distance_callback(from_index, to_index):
from_node = manager.IndexToNode(from_index)
to_node = manager.IndexToNode(to_index)
return int(distance_matrix[from_node][to_node] * 1000) # Convertir a enteros
transit_callback_index = routing.RegisterTransitCallback(distance_callback)
routing.SetArcCostEvaluatorOfAllVehicles(transit_callback_index)
# Par谩metros de soluci贸n
search_parameters = pywrapcp.DefaultRoutingSearchParameters()
search_parameters.first_solution_strategy = routing_enums_pb2.FirstSolutionStrategy.PATH_CHEAPEST_ARC
solution = routing.SolveWithParameters(search_parameters)
if solution:
index = routing.Start(0)
route = []
while not routing.IsEnd(index):
node_index = manager.IndexToNode(index)
if node_index > 0: # Omitir el nodo de inicio
debris_id = debris_data.iloc[node_index - 1]['debris_id']
x, y, z = all_points[node_index]
route.append((debris_id, x, y, z))
index = solution.Value(routing.NextVar(index))
logger.info("Ruta optimizada: %s", route)
return route
else:
logger.error("No se encontr贸 soluci贸n en la optimizaci贸n.")
return []
|