Skip to content
Snippets Groups Projects
Commit 6d12b765 authored by awenjb's avatar awenjb
Browse files

CSV reader in python

- some fixes in data_preprocess
- add csv_reader to read cleaned csv files
- update visualisation_map to show all routes in différent colors
parent 82161d31
No related branches found
No related tags found
No related merge requests found
using CSV, DataFrames, StatsBase, Random, Distributions
input = "/home/a24jacqb/Documents/Code/pdptw-main/julia/LCN_01.csv"
df = CSV.read(input, DataFrame)
......@@ -25,16 +24,18 @@ df.weight = map(extract_weight, df.comments)
df.weight = convert(Vector{Union{Missing, String}}, df.weight)
df.weight = replace!(df.weight, "" => missing)
select!(df, Not("comments")) # delete "comments"
println(first(df, 15))
df.weight = map(x -> ismissing(x) ? missing : replace(x, r"\s*kg" => ""), df.weight)
df.weight = map(x -> ismissing(x) ? missing : parse(Float64, x), df.weight)
select!(df, Not("comments")) # delete "comments"
function count_is_missing(column)
return count(x -> ismissing(x), column)
end
##################### modify / generate data
# remove doublon
df = unique(df)
......@@ -43,7 +44,6 @@ dropmissing!(df, ["# order"])
# fill missing data (weight & revenue) with a normal distribution
function fill_missing(value, type)
if ismissing(value) && type == "PICKUP"
new_value = round(rand(Normal(mu, sigma)), digits=2)
......@@ -55,7 +55,6 @@ function fill_missing(value, type)
end
end
df.weight = map(parse_weight, df.weight)
maxi = maximum(skipmissing(df.weight))
mu = mean(skipmissing(df.weight))
......@@ -72,4 +71,4 @@ end
println(first(df, 15))
CSV.write("clean_LCN_01.csv", df)
\ No newline at end of file
#CSV.write("clean_LCN_01.csv", df)
\ No newline at end of file
import json
import os
from typing import OrderedDict
import pandas as pd
import osmnx as ox
import networkx as nx
from datetime import datetime
class Location:
def __init__(self, id, longitude, latitude, demand, time_window,
service_duration, paired_location, loc_type):
self._id = id
self._longitude = longitude
self._latitude = latitude
self._demand = demand
self._time_window = time_window
self._service_duration = service_duration
self._paired_location = paired_location
self._loc_type = loc_type
def get_id(self):
return self._id
def get_longitude(self):
return self._longitude
def get_latitude(self):
return self._latitude
def get_demand(self):
return self._demand
def get_time_window(self):
return self._time_window
def get_service_duration(self):
return self._service_duration
def get_paired_location(self):
return self._paired_location
def get_loc_type(self):
return self._loc_type
def compute_matrix(locations, avg_speed_kmh=15):
coords = [(loc.get_latitude(), loc.get_longitude()) for loc in locations]
center_lat = locations[0].get_latitude()
center_lon = locations[0].get_longitude()
G = ox.graph_from_point((center_lat, center_lon), dist=10000, network_type='bike')
node_ids = ox.nearest_nodes(G, [lon for _, lon in coords], [lat for lat, _ in coords])
n = len(node_ids)
distance_matrix = [[0.0] * n for _ in range(n)]
time_matrix = [[0.0] * n for _ in range(n)]
for i in range(n):
for j in range(n):
if i == j:
distance_matrix[i][j] = 0.0
time_matrix[i][j] = 0.0
continue
try:
dist = nx.shortest_path_length(G, node_ids[i], node_ids[j], weight='length')
distance_matrix[i][j] = (dist / 1000.0)
time_matrix[i][j] = ((dist / 1000.0) / avg_speed_kmh) * 3600 # hours to seconds
except nx.NetworkXNoPath:
distance_matrix[i][j] = float("inf")
time_matrix[i][j] = float("inf")
return distance_matrix, time_matrix
def save_to_json(output_dir, filename, size, capacity, depot, locations, distance_matrix):
data = OrderedDict({
"size": size,
"capacity": capacity,
"depot": OrderedDict({
"id": depot.get_id(),
"longitude": depot.get_longitude(),
"latitude": depot.get_latitude(),
"demand": depot.get_demand(),
"timeWindow": depot.get_time_window(),
"serviceDuration": depot.get_service_duration(),
"pairedLocation": depot.get_paired_location(),
"locType": depot.get_loc_type()
}),
"locations": [OrderedDict({
"id": loc.get_id(),
"longitude": loc.get_longitude(),
"latitude": loc.get_latitude(),
"demand": loc.get_demand(),
"timeWindow": loc.get_time_window(),
"serviceDuration": loc.get_service_duration(),
"pairedLocation": loc.get_paired_location(),
"locType": loc.get_loc_type()
}) for loc in locations],
"distance_matrix": distance_matrix
})
output_path = os.path.join(output_dir, os.path.basename(filename) + ".json")
with open(output_path, "w") as f:
json.dump(data, f, indent=4)
def time_to_seconds(t: str) -> int:
h, m, s = map(float, t.split(":"))
return int(h * 3600 + m * 60 + s)
def read_day_requests(csv_file: str, target_day: str) -> list[Location]:
df = pd.read_csv(csv_file, sep=',')
df = df[df['afterDay'] == target_day]
# Locations
locations = []
for _, row in df.iterrows():
location_id = int(row['# order']) if not pd.isna(row['# order']) else None
if (row['type']=="PICKUP"):
loc_type = "PICKUP"
paired_location = (len(locations)+1) + 1
else :
loc_type = "DELIVERY"
paired_location = (len(locations)+1) - 1
lat, lon = map(float, row['address.latlng'].split(','))
demand = float(row['weight'])
start_time = time_to_seconds(str(row['afterTime']))
end_time = time_to_seconds(str(row['beforeTime']))
loc = Location(id=(len(locations)+1), longitude=lon, latitude=lat, demand=demand,
time_window=[start_time, end_time], service_duration=300,
paired_location=paired_location, loc_type=loc_type)
locations.append(loc)
# Depot
start_day = time_to_seconds(str(min(df['afterTime']))) - 1200
end_day = time_to_seconds(str(max(df['beforeTime']))) + 1200
depot = Location(id=0, longitude=-1.5461537253097524, latitude=47.20425475808151, demand=0,
time_window=[start_day, end_day], service_duration=0,
paired_location=0, loc_type="DEPOT")
return locations, depot
locations, depot = read_day_requests("julia/clean_LCN_01.csv", "03/10/2023")
size = len(locations) + 1
capacity = 275
copyLocations = list(locations)
copyLocations.insert(0, depot)
distance_matrix, time_matrix = compute_matrix(copyLocations)
save_to_json("data_in/Nantes/", "Nantes_03_10_2023", size, capacity, depot, locations, time_matrix)
......@@ -3,6 +3,7 @@ import datetime
import enum
import folium
from folium import Icon
import numpy as np
import pandas as pd
import osmnx as ox
......@@ -182,6 +183,7 @@ def display_route(map: folium.Map, data: PDPTWData, solution: PDPTWSolution, rou
for index, row in df.iterrows():
if row["type"] == "REQUEST":
text = f'{index} - {row["latitude"], row["longitude"]} : times ({row["arrival"]},{row["service"]},{row["departure"]}), time window [{row["Hmin"]},{row["Hmax"]}]'
folium.Circle(location=(row["latitude"], row["longitude"]), fill_color="orange", radius=4,
tooltip=text).add_to(map)
......
Source diff could not be displayed: it is too large. Options to address this: view the blob.
This diff is collapsed.
......@@ -13,7 +13,7 @@ int const ROUTE_PENALTY = 0;
int const NUMBER_VEHICLE = 50;
// Number of iterations for the algorithm or simulation to run.
int const NUMBER_ITERATION = 1000;
int const NUMBER_ITERATION = 10000;
// Flags
......@@ -27,11 +27,11 @@ int const RANDOM_SEED = 100;
bool const PRINT = true;
// Flag indicating whether the final solution is stored.
bool const STORE_SOLUTION = false;
bool const STORE_SOLUTION = true;
// Flag indicating whether the solution is stored with complete information or not.
bool const COMPLETE_STORE = true;
// Directories
std::string const OUTPUT_DIRECTORY = "./../../output/select_lc103";
\ No newline at end of file
std::string const OUTPUT_DIRECTORY = "./../../output";
\ No newline at end of file
......@@ -80,15 +80,15 @@ void simpleLNS(PDPTWData const &data, Solution &startingSolution)
output::exportToJson(result);
}
Solution sol = result.getBestSolution();
sol.print();
// try reduce the number of routes
BankFocusStringRemoval rem = BankFocusStringRemoval(10,10);
// Solution sol = result.getBestSolution();
// sol.print();
// // try reduce the number of routes
// BankFocusStringRemoval rem = BankFocusStringRemoval(10,10);
rem.destroySolution(sol);
// rem.destroySolution(sol);
std::cout << "final print" << std::endl;
sol.print();
// std::cout << "final print" << std::endl;
// sol.print();
}
......@@ -100,9 +100,10 @@ int main(int argc, char **argv)
///////////////////////////////////////////////////////////////////////
//std::string filepath = "/home/a24jacqb/Documents/Code/pdptw-main/data_in/n100/bar-n100-1.json";
std::string filepath = "/home/a24jacqb/Documents/Code/pdptw-main/data_in/pdp_100/lc103.json";
// std::string filepath = "/home/a24jacqb/Documents/Code/pdptw-main/data_in/pdp_100/lc103.json";
//std::string filepath = "/home/a24jacqb/Documents/Code/pdptw-main/data_in/Nantes_1.json";
//std::string filepath = "/home/a24jacqb/Documents/Code/pdptw-main/data_in/n5000/bar-n5000-1.json";
std::string filepath = "/home/a24jacqb/Documents/Code/pdptw-main/data_in/Nantes/Nantes_03_10_2023";
PDPTWData data = parsing::parseJson(filepath);
Solution startingSolution = Solution::emptySolution(data);
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment