._.
This commit is contained in:
parent
c8338ba142
commit
bd5aa7fcc6
@ -1,6 +1,8 @@
|
|||||||
from itertools import permutations
|
from itertools import permutations
|
||||||
from math import ceil
|
from math import ceil
|
||||||
|
from pprint import pprint
|
||||||
|
|
||||||
|
import requests
|
||||||
from sqlalchemy.orm import Session
|
from sqlalchemy.orm import Session
|
||||||
|
|
||||||
from app.infrastructure.database.repository.accessory_repository import AccessoriesRepository
|
from app.infrastructure.database.repository.accessory_repository import AccessoriesRepository
|
||||||
@ -8,6 +10,7 @@ from app.infrastructure.database.repository.city_repository import CityRepositor
|
|||||||
from app.infrastructure.database.repository.delivery_accessory_repository import DeliveryAccessoriesRepository
|
from app.infrastructure.database.repository.delivery_accessory_repository import DeliveryAccessoriesRepository
|
||||||
from app.infrastructure.database.repository.delivery_order_repository import DeliveryOrdersRepository
|
from app.infrastructure.database.repository.delivery_order_repository import DeliveryOrdersRepository
|
||||||
from app.infrastructure.database.repository.total_order_repository import TotalOrdersRepository
|
from app.infrastructure.database.repository.total_order_repository import TotalOrdersRepository
|
||||||
|
from app.infrastructure.database.repository.truck_repository import TrucksRepository
|
||||||
|
|
||||||
|
|
||||||
class NewTotalOrderService:
|
class NewTotalOrderService:
|
||||||
@ -17,38 +20,57 @@ class NewTotalOrderService:
|
|||||||
self.delivery_accessory_repository = DeliveryAccessoriesRepository(db)
|
self.delivery_accessory_repository = DeliveryAccessoriesRepository(db)
|
||||||
self.city_repository = CityRepository(db)
|
self.city_repository = CityRepository(db)
|
||||||
self.accessory_repository = AccessoriesRepository(db)
|
self.accessory_repository = AccessoriesRepository(db)
|
||||||
|
self.truck_repository = TrucksRepository(db)
|
||||||
|
|
||||||
def total_calculate(self):
|
def total_calculate(self):
|
||||||
|
print(111111111111111111111111111111111111111)
|
||||||
|
|
||||||
|
accessories = self.accessory_repository.get_with_cities_all()
|
||||||
|
cities = self.city_repository.get_all_with_federal_district()
|
||||||
|
tracks = self.truck_repository.get_all()
|
||||||
|
distances = self.create_distance_matrix(cities)
|
||||||
|
|
||||||
|
for i in distances:
|
||||||
|
for j in i:
|
||||||
|
print(j)
|
||||||
|
print()
|
||||||
|
|
||||||
grouped_by_period = self.group_accessories_by_period(accessories)
|
grouped_by_period = self.group_accessories_by_period(accessories)
|
||||||
routes_by_period = self.find_routes_by_period(grouped_by_period, distances, cities)
|
routes_by_period = self.find_routes_by_period(grouped_by_period, distances, cities)
|
||||||
|
|
||||||
|
response = ''
|
||||||
|
|
||||||
for period, routes in routes_by_period.items():
|
for period, routes in routes_by_period.items():
|
||||||
for route in routes:
|
for route in routes:
|
||||||
vehicle_count, selected_track = self.calculate_vehicle_requirements(
|
vehicle_count, selected_track = self.calculate_vehicle_requirements(
|
||||||
[a for a in accessories if a.period == period], tracks)
|
[a for a in accessories if a.period == period], tracks)
|
||||||
cost = self.calculate_route_cost(route, accessories, distances)
|
cost = self.calculate_route_cost(route, accessories, distances)
|
||||||
|
|
||||||
print(f"Период: {period}")
|
response += f"Период: {period}\n"
|
||||||
print(f"Маршрут: {' -> '.join([city.name for city in route])}")
|
response += f"Маршрут: {' -> '.join([city.name for city in route])}\n"
|
||||||
selected_vehicle_name = next((track.name for track in tracks if track.id == selected_track),
|
selected_vehicle_name = next((track.name for track in tracks if track.id == selected_track),
|
||||||
"Нет доступного автомобиля")
|
"Нет доступного автомобиля")
|
||||||
print(f"Тип автомобиля: {selected_vehicle_name}")
|
response += f"Тип автомобиля: {selected_vehicle_name}"
|
||||||
print(f"Количество автомобилей: {vehicle_count}")
|
response += f"Количество автомобилей: {vehicle_count}"
|
||||||
print(f"Стоимость перевозки: {cost}\n")
|
response += f"Стоимость перевозки: {cost}\n"
|
||||||
|
|
||||||
def find_routes_by_period(self, grouped_by_period, distances, cities):
|
def find_routes_by_period(self, grouped_by_period, distances, cities):
|
||||||
|
purpose_city_id = self.city_repository.get_by_name('Челябинск').id
|
||||||
|
|
||||||
routes_by_period = {}
|
routes_by_period = {}
|
||||||
|
|
||||||
for period, accessories in grouped_by_period.items():
|
for period, accessories in grouped_by_period.items():
|
||||||
cities_in_period = [next(city for city in cities if city.id == accessory.cityId) for accessory in
|
cities_in_period = [next(city for city in cities if city.id == accessory.city_id) for accessory in
|
||||||
accessories]
|
accessories]
|
||||||
all_routes = self.generate_routes(cities_in_period, next(city for city in cities if city.id == 9))
|
all_routes = self.generate_routes(cities_in_period,
|
||||||
|
next(city for city in cities if city.id == purpose_city_id))
|
||||||
|
|
||||||
routes_with_details = []
|
routes_with_details = []
|
||||||
for route in all_routes:
|
for route in all_routes:
|
||||||
distance = self.calculate_route_distance(route, distances)
|
distance = self.calculate_route_distance(route, distances)
|
||||||
total_weight = sum(
|
total_weight = sum(
|
||||||
sum(accessory.weight for accessory in accessories if accessory.cityId == city.id) for city in route)
|
sum(accessory.weight for accessory in accessories if accessory.city_id == city.id) for city in
|
||||||
|
route)
|
||||||
cost = self.calculate_route_cost(route, accessories, distances)
|
cost = self.calculate_route_cost(route, accessories, distances)
|
||||||
routes_with_details.append((route, (distance, total_weight, cost)))
|
routes_with_details.append((route, (distance, total_weight, cost)))
|
||||||
|
|
||||||
@ -57,6 +79,21 @@ class NewTotalOrderService:
|
|||||||
|
|
||||||
return routes_by_period
|
return routes_by_period
|
||||||
|
|
||||||
|
def create_distance_matrix(self, cities):
|
||||||
|
num_cities = len(cities)
|
||||||
|
distances = [[0] * num_cities for _ in range(num_cities)]
|
||||||
|
|
||||||
|
for i in range(num_cities):
|
||||||
|
for j in range(num_cities):
|
||||||
|
if i != j:
|
||||||
|
start_coords = (cities[i].x_coordinate, cities[i].y_coordinate)
|
||||||
|
end_coords = (cities[j].x_coordinate, cities[j].y_coordinate)
|
||||||
|
distances[i][j] = self.get_distance(start_coords, end_coords)
|
||||||
|
else:
|
||||||
|
distances[i][j] = 0
|
||||||
|
|
||||||
|
return distances
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def group_accessories_by_period(accessories):
|
def group_accessories_by_period(accessories):
|
||||||
grouped = {}
|
grouped = {}
|
||||||
@ -80,6 +117,7 @@ class NewTotalOrderService:
|
|||||||
@staticmethod
|
@staticmethod
|
||||||
def calculate_route_distance(route, distances):
|
def calculate_route_distance(route, distances):
|
||||||
total_distance = 0
|
total_distance = 0
|
||||||
|
pprint(distances)
|
||||||
for i in range(len(route) - 1):
|
for i in range(len(route) - 1):
|
||||||
total_distance += distances[route[i].id - 1][route[i + 1].id - 1]
|
total_distance += distances[route[i].id - 1][route[i + 1].id - 1]
|
||||||
return total_distance
|
return total_distance
|
||||||
@ -110,3 +148,17 @@ class NewTotalOrderService:
|
|||||||
selected_track = track.id
|
selected_track = track.id
|
||||||
|
|
||||||
return total_vehicles, selected_track
|
return total_vehicles, selected_track
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def get_distance(start_coords, end_coords):
|
||||||
|
base_url = "http://router.project-osrm.org/route/v1/driving"
|
||||||
|
url = f"{base_url}/{start_coords[1]},{start_coords[0]};{end_coords[1]},{end_coords[0]}?overview=full"
|
||||||
|
|
||||||
|
response = requests.get(url)
|
||||||
|
data = response.json()
|
||||||
|
|
||||||
|
if data['routes']:
|
||||||
|
distance = data['routes'][0]['distance'] / 1000
|
||||||
|
return distance
|
||||||
|
else:
|
||||||
|
return float('inf')
|
||||||
|
|||||||
@ -9,6 +9,9 @@ class CityRepository:
|
|||||||
def get_all(self):
|
def get_all(self):
|
||||||
return self.db.query(City).all()
|
return self.db.query(City).all()
|
||||||
|
|
||||||
|
def get_by_name(self, city_name):
|
||||||
|
return self.db.query(City).filter(City.name == city_name).first()
|
||||||
|
|
||||||
def get_all_with_federal_district(self):
|
def get_all_with_federal_district(self):
|
||||||
return self.db.query(City) \
|
return self.db.query(City) \
|
||||||
.options(joinedload(City.federal_district)) \
|
.options(joinedload(City.federal_district)) \
|
||||||
|
|||||||
@ -4,6 +4,7 @@ from fastapi import APIRouter, HTTPException, Depends
|
|||||||
from sqlalchemy.orm import Session
|
from sqlalchemy.orm import Session
|
||||||
|
|
||||||
from app.core.usecases.auth_service import verify_token
|
from app.core.usecases.auth_service import verify_token
|
||||||
|
from app.core.usecases.new_total_order_service import NewTotalOrderService
|
||||||
from app.infrastructure.database.dependencies import get_db
|
from app.infrastructure.database.dependencies import get_db
|
||||||
from app.core.entities.total_order import TotalOrderEntity
|
from app.core.entities.total_order import TotalOrderEntity
|
||||||
from app.core.usecases.total_order_service import TotalOrdersService
|
from app.core.usecases.total_order_service import TotalOrdersService
|
||||||
@ -54,3 +55,9 @@ def delete_total_order(total_order_id: int, db: Session = Depends(get_db),
|
|||||||
if not success:
|
if not success:
|
||||||
raise HTTPException(status_code=404, detail="Total order not found")
|
raise HTTPException(status_code=404, detail="Total order not found")
|
||||||
return success
|
return success
|
||||||
|
|
||||||
|
|
||||||
|
@router.post("/total-orders/calculate", response_model=TotalOrderEntity)
|
||||||
|
def calculate_total_order(db: Session = Depends(get_db)):
|
||||||
|
service = NewTotalOrderService(db)
|
||||||
|
return service.total_calculate()
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user