diff --git a/NEWS.md b/NEWS.md index cab8ec543..19c64c608 100644 --- a/NEWS.md +++ b/NEWS.md @@ -14,7 +14,8 @@ on Github. * Renamed files to be compiled as C++ with .hpp & .cpp extensions * Moved sphinx doc from .c files .rst files -* removing prefix `pgr_` & addding `namespace vrprouting` +* Removing prefix `pgr_` & addding `namespace vrprouting` +* Separating implementation from header vroom.hpp **Documentation queries** diff --git a/doc/general/release_notes.rst b/doc/general/release_notes.rst index e09ba3365..2baa4efa7 100644 --- a/doc/general/release_notes.rst +++ b/doc/general/release_notes.rst @@ -49,7 +49,8 @@ on Github. * Renamed files to be compiled as C++ with .hpp & .cpp extensions * Moved sphinx doc from .c files .rst files -* removing prefix `pgr_` & addding `namespace vrprouting` +* Removing prefix `pgr_` & addding `namespace vrprouting` +* Separating implementation from header vroom.hpp .. rubric:: Documentation queries diff --git a/include/vroom/vroom.hpp b/include/vroom/vroom.hpp index 4cbc5b210..704be0955 100644 --- a/include/vroom/vroom.hpp +++ b/include/vroom/vroom.hpp @@ -29,623 +29,84 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. #define INCLUDE_VROOM_VROOM_HPP_ #pragma once +#include +#include +#include + #include #include #include #include #include -#include "cpp_common/matrix_cell_t.hpp" -#include "cpp_common/vroom_break_t.hpp" -#include "cpp_common/vroom_job_t.hpp" -#include "c_types/vroom_rt.h" -#include "cpp_common/vroom_shipment_t.hpp" -#include "cpp_common/vroom_time_window_t.hpp" -#include "cpp_common/vroom_vehicle_t.hpp" +#include "c_types/typedefs.h" #include "cpp_common/base_matrix.hpp" -#include "cpp_common/interruption.hpp" #include "cpp_common/messages.hpp" -#include "structures/vroom/input/input.h" -#include "structures/vroom/job.h" -#include "structures/vroom/vehicle.h" + +using Vroom_rt = struct Vroom_rt; namespace vrprouting { +namespace problem { -class Vrp_vroom_problem : public vrprouting::Messages { +class Vroom : public vrprouting::Messages { public: - std::vector jobs() const { return m_jobs; } - std::vector> shipments() const { return m_shipments; } - std::vector vehicles() const { return m_vehicles; } - vrprouting::base::Base_Matrix matrix() const { return m_matrix; } - - /** - * @name vroom time window wrapper - */ - ///@{ - /** - * @brief Gets the vroom time window from the C-style struct - * - * @param[in] time_window The C-style time window struct - * - * @return The vroom time window. - */ - vroom::TimeWindow - get_vroom_time_window(const Vroom_time_window_t &time_window) const { - return - vroom::TimeWindow(time_window.tw_open, - time_window.tw_close); - } - - vroom::TimeWindow - get_vroom_time_window(Duration tw_open, Duration tw_close) const { - return vroom::TimeWindow(tw_open, tw_close); - } - - std::vector - get_vroom_time_windows( - const std::vector &time_windows) const { - std::vector < vroom::TimeWindow > tws; - for (auto time_window : time_windows) { - tws.push_back(get_vroom_time_window(time_window)); - } - if (tws.size()) { - return tws; - } else { - return std::vector(1, vroom::TimeWindow()); - } - } - ///@} - - - /** - * @name vroom amounts wrapper - */ - ///@{ - /** - * @brief Gets the vroom amounts from C-style array - * - * @param[in] amounts The amounts array (pickup or delivery) - * - * @return The vroom amounts. - */ - vroom::Amount - get_vroom_amounts(const std::vector &amounts) const { - vroom::Amount amt; - if (amounts.size()) { - for (auto amount : amounts) { - amt.push_back(amount); - } - } else { - const unsigned int amount_size = - m_vehicles.size() ? static_cast(m_vehicles[0].capacity.size()) : 0; - // Default to zero amount with provided size. - amt = vroom::Amount(amount_size); - for (size_t i = 0; i < amounts.size(); i++) { - amt[i] = amounts[i]; - } - } - return amt; - } - - vroom::Amount - get_vroom_amounts(const Amount *amounts, size_t count) const { - return get_vroom_amounts(std::vector (amounts, amounts + count)); - } - ///@} - - - /** - * @name vroom skills wrapper - */ - ///@{ - /** - * @brief Gets the vroom skills. - * - * @param[in] skills The skills array - * @param[in] count The size of skills array - * - * @return The vroom skills. - */ - vroom::Skills - get_vroom_skills(const Skill *skills, size_t count) const { - return std::unordered_set (skills, skills + count); - } - ///@} - - - /** - * @name vroom jobs wrapper - */ - ///@{ - /** - * @brief Gets the vroom jobs. - * - * @param[in] job The job C-style struct - * @param[in] job_tws The job time windows - * - * @return The vroom job. - */ - vroom::Job - get_vroom_job(const Vroom_job_t &job, - const std::vector &job_tws) const { - vroom::Amount delivery = - get_vroom_amounts(job.delivery, job.delivery_size); - vroom::Amount pickup = - get_vroom_amounts(job.pickup, job.pickup_size); - vroom::Skills skills = - get_vroom_skills(job.skills, job.skills_size); - std::vector time_windows = - get_vroom_time_windows(job_tws); - vroom::Index location_id = - static_cast(m_matrix.get_index(job.location_id)); - return vroom::Job(job.id, location_id, job.setup, job.service, delivery, pickup, - skills, job.priority, time_windows, job.data); - } - - void problem_add_job(const Vroom_job_t &job, - const std::vector &job_tws) { - m_jobs.push_back(get_vroom_job(job, job_tws)); - } - - void add_jobs(const std::vector &jobs, - const std::vector &jobs_tws) { - std::map> job_tws_map; - for (auto job_tw : jobs_tws) { - Idx id = job_tw.id; - if (job_tws_map.find(id) == job_tws_map.end()) { - job_tws_map[id] = std::vector(); - } - job_tws_map[id].push_back(job_tw); - } - for (auto job : jobs) { - problem_add_job(job, job_tws_map[job.id]); - } - } - - void add_jobs(const Vroom_job_t *jobs, size_t count, - const Vroom_time_window_t *jobs_tws, size_t total_jobs_tws) { - add_jobs( - std::vector(jobs, jobs + count), - std::vector(jobs_tws, jobs_tws + total_jobs_tws)); - } - ///@} - - - /** - * @name vroom shipments wrapper - */ - ///@{ - /** - * @brief Gets the vroom shipments. - * - * @param[in] shipment The shipment C-style struct - * @param[in] pickup_tws The pickup time windows - * @param[in] delivery_tws The delivery time windows - * - * @return The vroom shipment. - */ - std::pair get_vroom_shipment( - const Vroom_shipment_t &shipment, - const std::vector &pickup_tws, - const std::vector &delivery_tws) const { - vroom::Amount amount = - get_vroom_amounts(shipment.amount, shipment.amount_size); - vroom::Skills skills = - get_vroom_skills(shipment.skills, shipment.skills_size); - std::vector p_time_windows = - get_vroom_time_windows(pickup_tws); - std::vector d_time_windows = - get_vroom_time_windows(delivery_tws); - vroom::Index p_location_id = static_cast( - m_matrix.get_index(shipment.p_location_id)); - vroom::Index d_location_id = static_cast( - m_matrix.get_index(shipment.d_location_id)); - vroom::Job pickup = vroom::Job( - shipment.id, vroom::JOB_TYPE::PICKUP, p_location_id, - shipment.p_setup, shipment.p_service, amount, - skills, shipment.priority, p_time_windows, shipment.p_data); - vroom::Job delivery = vroom::Job( - shipment.id, vroom::JOB_TYPE::DELIVERY, d_location_id, - shipment.d_setup, shipment.d_service, amount, - skills, shipment.priority, d_time_windows, shipment.d_data); - return std::make_pair(pickup, delivery); - } - - void problem_add_shipment( - const Vroom_shipment_t &shipment, - const std::vector &pickup_tws, - const std::vector &delivery_tws) { - m_shipments.push_back( - get_vroom_shipment(shipment, pickup_tws, delivery_tws)); - } - - void add_shipments(const std::vector &shipments, - const std::vector &shipments_tws) { - std::map> pickup_tws_map; - std::map> delivery_tws_map; - for (auto shipment_tw : shipments_tws) { - Idx id = shipment_tw.id; - if (shipment_tw.kind == 'p') { - if (pickup_tws_map.find(id) == pickup_tws_map.end()) { - pickup_tws_map[id] = std::vector(); - } - pickup_tws_map[id].push_back(shipment_tw); - } else if (shipment_tw.kind == 'd') { - if (delivery_tws_map.find(id) == delivery_tws_map.end()) { - delivery_tws_map[id] = std::vector(); - } - delivery_tws_map[id].push_back(shipment_tw); - } - } - for (auto shipment : shipments) { - problem_add_shipment(shipment, pickup_tws_map[shipment.id], - delivery_tws_map[shipment.id]); - } - } - - void add_shipments(const Vroom_shipment_t *shipments, size_t count, - const Vroom_time_window_t *shipment_tws, size_t total_shipment_tws) { - add_shipments( - std::vector(shipments, shipments + count), - std::vector(shipment_tws, shipment_tws + total_shipment_tws)); - } - ///@} - - - /** - * @name vroom breaks wrapper - */ - ///@{ - /** - * @brief Gets the vehicle breaks from C-style breaks struct - * - * @param[in] v_break The vehicle break struct - * - * @return The vroom vehicle break. - */ - vroom::Break - get_vroom_break( - const Vroom_break_t &v_break, - const std::vector &break_tws) const { - std::vector tws = get_vroom_time_windows(break_tws); - return vroom::Break(v_break.id, tws, v_break.service, v_break.data); - } - - std::vector < vroom::Break > - get_vroom_breaks( - const std::vector &breaks, - const std::vector &breaks_tws) const { - std::map> breaks_tws_map; - for (auto break_tw : breaks_tws) { - Idx id = break_tw.id; - if (breaks_tws_map.find(id) == breaks_tws_map.end()) { - breaks_tws_map[id] = std::vector(); - } - breaks_tws_map[id].push_back(break_tw); - } - std::vector < vroom::Break > v_breaks; - for (auto v_break : breaks) { - v_breaks.push_back(get_vroom_break(v_break, breaks_tws_map[v_break.id])); - } - return v_breaks; - } - ///@} + /** @brief sets m_jobs by adding the Vroom_job_t */ + void add_jobs( + const std::vector&, + const std::vector&); + void add_jobs(const Vroom_job_t*, size_t, const Vroom_time_window_t*, size_t); + + /** @brief sets m_shipments by adding the Vroom_shipment_t */ + void add_shipments( + const std::vector&, + const std::vector&); + void add_shipments(const Vroom_shipment_t*, size_t, const Vroom_time_window_t*, size_t); + + /** @brief sets m_vehicles by adding the Vroom_vehicle_t */ + void add_vehicles( + const std::vector&, + const std::vector&, + const std::vector&); + void add_vehicles(const Vroom_vehicle_t*, size_t, const Vroom_break_t*, size_t, const Vroom_time_window_t*, size_t); + + /** @brief sets m_matrix */ + void add_matrix(const vrprouting::base::Base_Matrix&); + + /** @brief solves the vroom problem */ + std::vector solve(int32_t, int32_t, int32_t); - - /** - * @name vroom vehicles wrapper - */ - ///@{ - /** - * @brief Gets the vroom vehicles. - * - * @param[in] vehicle The vehicle C-style struct - * @param[in] breaks_tws The breaks time windows - * - * @return The vroom vehicle. - */ - vroom::Vehicle get_vroom_vehicle( - const Vroom_vehicle_t &vehicle, - const std::vector &breaks, - const std::vector &breaks_tws) const { - vroom::Amount capacity = - get_vroom_amounts(vehicle.capacity, vehicle.capacity_size); - vroom::Skills skills = - get_vroom_skills(vehicle.skills, vehicle.skills_size); - vroom::TimeWindow time_window = - get_vroom_time_window(vehicle.tw_open, - vehicle.tw_close); - std::vector v_breaks = get_vroom_breaks(breaks, breaks_tws); - - std::optional start_id; - std::optional end_id; - // Set the value of start or end index only if they are present - if (vehicle.start_id != -1) { - start_id = static_cast(m_matrix.get_index(vehicle.start_id)); - } - if (vehicle.end_id != -1) { - end_id = static_cast(m_matrix.get_index(vehicle.end_id)); - } - return vroom::Vehicle(vehicle.id, start_id, end_id, - vroom::DEFAULT_PROFILE, capacity, skills, time_window, - v_breaks, vehicle.data, vehicle.speed_factor, - static_cast(vehicle.max_tasks)); - } - - void problem_add_vehicle( - const Vroom_vehicle_t &vehicle, - const std::vector &breaks, - const std::vector &breaks_tws) { - m_vehicles.push_back(get_vroom_vehicle(vehicle, breaks, breaks_tws)); - } - - void add_vehicles(const std::vector &vehicles, - const std::vector &breaks, - const std::vector &breaks_tws) { - std::map> breaks_tws_map; - for (auto break_tw : breaks_tws) { - Idx id = break_tw.id; - if (breaks_tws_map.find(id) == breaks_tws_map.end()) { - breaks_tws_map[id] = std::vector(); - } - breaks_tws_map[id].push_back(break_tw); - } - - std::map> v_breaks_map; - for (auto v_break : breaks) { - Idx v_id = v_break.vehicle_id; - if (v_breaks_map.find(v_id) == v_breaks_map.end()) { - v_breaks_map[v_id] = std::vector(); - } - v_breaks_map[v_id].push_back(v_break); - } - - for (auto vehicle : vehicles) { - std::vector v_breaks = v_breaks_map[vehicle.id]; - std::vector v_breaks_tws; - for (auto v_break : v_breaks) { - std::vector tws = breaks_tws_map[v_break.id]; - v_breaks_tws.insert(v_breaks_tws.end(), tws.begin(), tws.end()); - } - problem_add_vehicle(vehicle, v_breaks, v_breaks_tws); - } - } - - void add_vehicles(const Vroom_vehicle_t *vehicles, size_t count, - const Vroom_break_t *breaks, size_t total_breaks, - const Vroom_time_window_t *breaks_tws, size_t total_breaks_tws) { - add_vehicles(std::vector(vehicles, vehicles + count), - std::vector(breaks, breaks + total_breaks), - std::vector(breaks_tws, breaks_tws + total_breaks_tws)); - } - ///@} - - - void add_matrix(vrprouting::base::Base_Matrix matrix) { - m_matrix = matrix; - } - - void get_amount(vroom::Amount vroom_amount, Amount **amount) { - size_t amount_size = vroom_amount.size(); - for (size_t i = 0; i < amount_size; i++) { - *((*amount) + i) = vroom_amount[i]; - } - } - - StepType get_job_step_type(vroom::JOB_TYPE vroom_job_type) { - StepType step_type; - switch (vroom_job_type) { - case vroom::JOB_TYPE::SINGLE: - step_type = 2; - break; - case vroom::JOB_TYPE::PICKUP: - step_type = 3; - break; - case vroom::JOB_TYPE::DELIVERY: - step_type = 4; - break; - } - return step_type; - } - - StepType get_step_type(vroom::Step step) { - StepType step_type = 0; - switch (step.step_type) { - case vroom::STEP_TYPE::START: - step_type = 1; - break; - case vroom::STEP_TYPE::END: - step_type = 6; - break; - case vroom::STEP_TYPE::BREAK: - step_type = 5; - break; - case vroom::STEP_TYPE::JOB: - step_type = get_job_step_type(step.job_type); - break; - } - return step_type; - } - - std::vector < Vroom_rt > get_results(vroom::Solution solution) { - std::vector < Vroom_rt > results; - std::vector routes = solution.routes; - Idx vehicle_seq = 1; - char *empty_desc = strdup("{}"); - for (auto route : routes) { - Idx step_seq = 1; - Duration prev_duration = 0; - char *vehicle_data = strdup(route.description.c_str()); - for (auto step : route.steps) { - Idx task_id = step.id; - MatrixIndex location_id = m_matrix.get_original_id(step.location.index()); - char *task_data = strdup(step.description.c_str()); - StepType step_type = get_step_type(step); - if (step_type == 1 || step_type == 6) { - task_id = static_cast(-1); - task_data = empty_desc; - } - - size_t load_size = step.load.size(); - Amount *load = reinterpret_cast(malloc(load_size * sizeof(Amount))); - get_amount(step.load, &load); - - Duration travel_time = step.duration - prev_duration; - prev_duration = step.duration; - Duration departure = step.arrival + step.setup + step.service + step.waiting_time; - results.push_back({ - vehicle_seq, // vehicles_seq - route.vehicle, // vehicles_id - vehicle_data, // vehicle_data - step_seq, // step_seq - step_type, // step_type - task_id, // task_id - location_id, // location_id - task_data, // task_data - step.arrival, // arrival - travel_time, // travel_time - step.setup, // setup_time - step.service, // service_time - step.waiting_time, // waiting_time - departure, // departure - load, // load - load_size // load size - }); - step_seq++; - } - // The summary of this route - Idx task_id = 0; - results.push_back({ - vehicle_seq, // vehicles_seq - route.vehicle, // vehicles_id - vehicle_data, // vehicle_data - 0, // step_seq = 0 for route summary - 0, // step_type = 0 for route summary - task_id, // task_id = 0 for route summary - 0, // location_id = 0 for route summary - empty_desc, // task_data - 0, // No arrival time - route.duration, // Total travel time - route.setup, // Total setup time - route.service, // Total service time - route.waiting_time, // Total waiting time - 0, // No departure time - {}, // load - 0 // load size - }); - vehicle_seq++; - } - - std::vector unassigned = solution.unassigned; - Idx step_seq = 1; - for (auto job : unassigned) { - StepType job_step = get_job_step_type(job.type); - Idx vehicle_id = static_cast(-1); - Idx job_id = job.id; - MatrixIndex location_id = m_matrix.get_original_id(job.location.index()); - char *task_data = strdup(job.description.c_str()); - results.push_back({ - vehicle_seq, // vehicles_seq - vehicle_id, // vehicles_id = -1 for unassigned jobs - empty_desc, // vehicle_data - step_seq, // step_seq - job_step, // step_type - job_id, // task_id - location_id, // location_id - task_data, // task_data - 0, // No arrival time - 0, // No travel_time - 0, // No setup_time - 0, // No service_time - 0, // No waiting_time - 0, // No departure time - {}, // load - 0 // load size - }); - step_seq++; - } - - // The summary of the entire problem - vroom::Summary summary = solution.summary; - Idx vehicle_id = 0; - Idx job_id = 0; - results.push_back({ - 0, // vehicles_seq = 0 for problem summary - vehicle_id, // vehicles_id = 0 for problem summary - empty_desc, // vehicle_data - 0, // step_seq = 0 for problem summary - 0, // step_type = 0 for problem summary - job_id, // task_id = 0 for problem summary - 0, // location_id = 0 for problem summary - empty_desc, // task_data - 0, // No arrival time - summary.duration, // Total travel time - summary.setup, // Total setup time - summary.service, // Total service time - summary.waiting_time, // Total waiting time - 0, // No departure time - {}, // load - 0 // load size - }); - return results; - } - - std::vector solve(int32_t exploration_level, int32_t timeout, - int32_t loading_time) { - std::vector results; - - /* abort in case an interruption occurs (e.g. the query is being cancelled) */ - CHECK_FOR_INTERRUPTS(); - try { - const unsigned int amount_size = - m_vehicles.size() - ? static_cast(m_vehicles[0].capacity.size()) - : 0; - vroom::Input problem_instance; - problem_instance.set_amount_size(amount_size); - - for (const auto &vehicle : m_vehicles) { - problem_instance.add_vehicle(vehicle); - } - for (const auto &job : m_jobs) { - problem_instance.add_job(job); - } - for (const auto &shipment : m_shipments) { - problem_instance.add_shipment(shipment.first, shipment.second); - } - vroom::Matrix duration_matrix = m_matrix.get_vroom_duration_matrix(); - vroom::Matrix cost_matrix = m_matrix.get_vroom_cost_matrix(); - problem_instance.set_durations_matrix(vroom::DEFAULT_PROFILE, std::move(duration_matrix)); - problem_instance.set_costs_matrix(vroom::DEFAULT_PROFILE, std::move(cost_matrix)); - - unsigned threads = 4; - if (timeout < 0) { - auto solution = problem_instance.solve( - static_cast(exploration_level), threads); - results = get_results(solution); - } else { - int timeout_ms = (loading_time <= timeout * 1000) ? (timeout * 1000 - loading_time) : 0; - auto solution = problem_instance.solve( - static_cast(exploration_level), threads, timeout_ms); - results = get_results(solution); - } - } catch (const vroom::Exception &ex) { - throw; - } catch (const std::exception &ex) { - throw; - } catch (...) { - throw; - } - return results; - } + private: + std::vector get_vroom_time_windows(const std::vector&) const; + vroom::Amount get_vroom_amounts(const std::vector&) const; + vroom::Amount get_vroom_amounts(const Amount *amounts, size_t count) const; + vroom::Skills get_vroom_skills(const Skill*, size_t) const; + vroom::Job get_vroom_job( + const Vroom_job_t&, + const std::vector&) const; + std::pair get_vroom_shipment( + const Vroom_shipment_t&, + const std::vector&, + const std::vector&) const; + std::vector get_vroom_breaks( + const std::vector&, + const std::vector&) const; + vroom::Vehicle get_vroom_vehicle( + const Vroom_vehicle_t&, + const std::vector&, + const std::vector&) const; + void get_amount(vroom::Amount, Amount**); + StepType get_job_step_type(vroom::JOB_TYPE); + StepType get_step_type(vroom::Step); + std::vector get_results(vroom::Solution); private: - std::vector m_jobs; - std::vector> m_shipments; - std::vector m_vehicles; - vrprouting::base::Base_Matrix m_matrix; + std::vector m_jobs; + std::vector> m_shipments; + std::vector m_vehicles; + vrprouting::base::Base_Matrix m_matrix; }; +} // namespace problem } // namespace vrprouting #endif // INCLUDE_VROOM_VROOM_HPP_ diff --git a/locale/en/LC_MESSAGES/release_notes.po b/locale/en/LC_MESSAGES/release_notes.po index 39145805a..52006f43f 100644 --- a/locale/en/LC_MESSAGES/release_notes.po +++ b/locale/en/LC_MESSAGES/release_notes.po @@ -8,14 +8,14 @@ msgid "" msgstr "" "Project-Id-Version: vrpRouting v0.0.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2024-08-06 20:01+0000\n" +"POT-Creation-Date: 2024-08-10 18:38+0000\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME \n" "Language-Team: LANGUAGE \n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" -"Generated-By: Babel 2.15.0\n" +"Generated-By: Babel 2.16.0\n" #: ../../build/doc/release_notes.rst:12 msgid "" @@ -86,26 +86,30 @@ msgid "Moved sphinx doc from .c files .rst files" msgstr "" #: ../../build/doc/release_notes.rst:52 -msgid "removing prefix `pgr_` & addding `namespace vrprouting`" +msgid "Removing prefix `pgr_` & addding `namespace vrprouting`" msgstr "" -#: ../../build/doc/release_notes.rst:56 -msgid "Documentation queries" +#: ../../build/doc/release_notes.rst:53 +msgid "Separating implementation from header vroom.hpp" msgstr "" #: ../../build/doc/release_notes.rst:57 -msgid "Renamed to extension `.pg`" +msgid "Documentation queries" msgstr "" #: ../../build/doc/release_notes.rst:58 +msgid "Renamed to extension `.pg`" +msgstr "" + +#: ../../build/doc/release_notes.rst:59 msgid "Removed `doc-` and `doc-vrp_` suffixes on file names" msgstr "" -#: ../../build/doc/release_notes.rst:61 +#: ../../build/doc/release_notes.rst:62 msgid "vrpRouting 0.4.1 Release Notes" msgstr "" -#: ../../build/doc/release_notes.rst:63 +#: ../../build/doc/release_notes.rst:64 #, python-format msgid "" "To see all issues & pull requests closed by this release see the `Git " @@ -114,23 +118,23 @@ msgid "" " on Github." msgstr "" -#: ../../build/doc/release_notes.rst:69 +#: ../../build/doc/release_notes.rst:70 msgid "Modification on experimental functions" msgstr "" -#: ../../build/doc/release_notes.rst:70 +#: ../../build/doc/release_notes.rst:71 msgid "OR Tools" msgstr "" -#: ../../build/doc/release_notes.rst:72 +#: ../../build/doc/release_notes.rst:73 msgid "vrp_bin_packing" msgstr "" -#: ../../build/doc/release_notes.rst:73 +#: ../../build/doc/release_notes.rst:74 msgid "vrp_knapsack" msgstr "" -#: ../../build/doc/release_notes.rst:74 +#: ../../build/doc/release_notes.rst:75 msgid "vrp_multiple_knapsack" msgstr "" @@ -138,7 +142,7 @@ msgstr "" msgid "Support for or-tools v9.10.4067" msgstr "" -#: ../../build/doc/release_notes.rst:80 +#: ../../build/doc/release_notes.rst:81 msgid "vrp_oneDepot" msgstr "" @@ -150,15 +154,15 @@ msgstr "" msgid "Result columns changed" msgstr "" -#: ../../build/doc/release_notes.rst:87 +#: ../../build/doc/release_notes.rst:88 msgid "Removal of Boost on the build" msgstr "" -#: ../../build/doc/release_notes.rst:88 ../../build/doc/release_notes.rst:186 +#: ../../build/doc/release_notes.rst:89 ../../build/doc/release_notes.rst:187 msgid "vrp_full_version" msgstr "" -#: ../../build/doc/release_notes.rst:89 ../../build/doc/release_notes.rst:185 +#: ../../build/doc/release_notes.rst:90 ../../build/doc/release_notes.rst:186 msgid "vrp_version" msgstr "" @@ -166,11 +170,11 @@ msgstr "" msgid "Boost removed from the result columns" msgstr "" -#: ../../build/doc/release_notes.rst:96 +#: ../../build/doc/release_notes.rst:97 msgid "vrpRouting 0.4.0 Release Notes" msgstr "" -#: ../../build/doc/release_notes.rst:98 +#: ../../build/doc/release_notes.rst:99 #, python-format msgid "" "To see all issues & pull requests closed by this release see the `Git " @@ -179,39 +183,39 @@ msgid "" " on Github." msgstr "" -#: ../../build/doc/release_notes.rst:103 +#: ../../build/doc/release_notes.rst:104 msgid "" "Added support for VROOM 1.12.0 (`#34 " "`_)" msgstr "" -#: ../../build/doc/release_notes.rst:104 +#: ../../build/doc/release_notes.rst:105 msgid "No visible changes on user side with respect to signatures." msgstr "" -#: ../../build/doc/release_notes.rst:105 +#: ../../build/doc/release_notes.rst:106 msgid "Adjusted to VROOM v1.12.0 due to internal breaking changes:" msgstr "" -#: ../../build/doc/release_notes.rst:107 +#: ../../build/doc/release_notes.rst:108 msgid "Made changes according to new vroom::Input signature." msgstr "" -#: ../../build/doc/release_notes.rst:108 +#: ../../build/doc/release_notes.rst:109 msgid "" "CI changes to compile without routing support, with Position Independent " "Code." msgstr "" -#: ../../build/doc/release_notes.rst:109 +#: ../../build/doc/release_notes.rst:110 msgid "Removed support for VROOM 1.11.0" msgstr "" -#: ../../build/doc/release_notes.rst:112 +#: ../../build/doc/release_notes.rst:113 msgid "vrpRouting 0.3" msgstr "" -#: ../../build/doc/release_notes.rst:114 +#: ../../build/doc/release_notes.rst:115 #, python-format msgid "" "To see all issues & pull requests closed by this release see the `Git " @@ -220,87 +224,87 @@ msgid "" " on Github." msgstr "" -#: ../../build/doc/release_notes.rst:119 +#: ../../build/doc/release_notes.rst:120 msgid "Modification of experimental functions" msgstr "" -#: ../../build/doc/release_notes.rst:120 ../../build/doc/release_notes.rst:158 +#: ../../build/doc/release_notes.rst:121 ../../build/doc/release_notes.rst:159 msgid "VROOM" msgstr "" -#: ../../build/doc/release_notes.rst:122 ../../build/doc/release_notes.rst:160 +#: ../../build/doc/release_notes.rst:123 ../../build/doc/release_notes.rst:161 msgid "vrp_vroom" msgstr "" -#: ../../build/doc/release_notes.rst:123 ../../build/doc/release_notes.rst:161 +#: ../../build/doc/release_notes.rst:124 ../../build/doc/release_notes.rst:162 msgid "vrp_vroomJobs" msgstr "" -#: ../../build/doc/release_notes.rst:124 ../../build/doc/release_notes.rst:162 +#: ../../build/doc/release_notes.rst:125 ../../build/doc/release_notes.rst:163 msgid "vrp_vroomShipments" msgstr "" -#: ../../build/doc/release_notes.rst:125 ../../build/doc/release_notes.rst:163 +#: ../../build/doc/release_notes.rst:126 ../../build/doc/release_notes.rst:164 msgid "vrp_vroomPlain" msgstr "" -#: ../../build/doc/release_notes.rst:126 ../../build/doc/release_notes.rst:164 +#: ../../build/doc/release_notes.rst:127 ../../build/doc/release_notes.rst:165 msgid "vrp_vroomJobsPlain" msgstr "" -#: ../../build/doc/release_notes.rst:127 ../../build/doc/release_notes.rst:165 +#: ../../build/doc/release_notes.rst:128 ../../build/doc/release_notes.rst:166 msgid "vrp_vroomShipmentsPlain" msgstr "" -#: ../../build/doc/release_notes.rst:130 +#: ../../build/doc/release_notes.rst:131 msgid "" "Added support for VROOM 1.11.0 (`#24 " "`_)" msgstr "" -#: ../../build/doc/release_notes.rst:131 +#: ../../build/doc/release_notes.rst:132 msgid "Added setup time in jobs and shipments to refine service time modeling." msgstr "" -#: ../../build/doc/release_notes.rst:132 +#: ../../build/doc/release_notes.rst:133 msgid "Added support for custom cost matrices, along with the duration matrix." msgstr "" -#: ../../build/doc/release_notes.rst:134 +#: ../../build/doc/release_notes.rst:135 msgid "Using start_id, end_id, duration, cost as matrix table columns." msgstr "" -#: ../../build/doc/release_notes.rst:135 +#: ../../build/doc/release_notes.rst:136 msgid "" "Added timeout and exploration_level parameters to vroom-category " "functions." msgstr "" -#: ../../build/doc/release_notes.rst:136 +#: ../../build/doc/release_notes.rst:137 msgid "Added max_tasks column in vehicles." msgstr "" -#: ../../build/doc/release_notes.rst:137 +#: ../../build/doc/release_notes.rst:138 msgid "Added tests for empty skills arrays." msgstr "" -#: ../../build/doc/release_notes.rst:138 +#: ../../build/doc/release_notes.rst:139 msgid "Added custom scaling logic for speed_factor." msgstr "" -#: ../../build/doc/release_notes.rst:139 +#: ../../build/doc/release_notes.rst:140 msgid "Modified parameter names to make the naming consistent." msgstr "" -#: ../../build/doc/release_notes.rst:142 +#: ../../build/doc/release_notes.rst:143 msgid "Fixes" msgstr "" -#: ../../build/doc/release_notes.rst:143 +#: ../../build/doc/release_notes.rst:144 msgid "Honor client cancel requests for vroom-category functions." msgstr "" -#: ../../build/doc/release_notes.rst:144 +#: ../../build/doc/release_notes.rst:145 msgid "" "Added more information in the inner query and result columns of VROOM " "category functions (`#26 " @@ -308,79 +312,79 @@ msgid "" "`_):" msgstr "" -#: ../../build/doc/release_notes.rst:147 +#: ../../build/doc/release_notes.rst:148 msgid "Summary row in the output, for each vehicle and for the complete problem." msgstr "" -#: ../../build/doc/release_notes.rst:148 +#: ../../build/doc/release_notes.rst:149 msgid "Uassigned rows in the output with vehicle_id = -1." msgstr "" -#: ../../build/doc/release_notes.rst:149 +#: ../../build/doc/release_notes.rst:150 msgid "" "Modified travel_time result column to return travel time between current " "and last step." msgstr "" -#: ../../build/doc/release_notes.rst:150 +#: ../../build/doc/release_notes.rst:151 msgid "" "Added data jsonb field in jobs, shipments, vehicles, breaks as well as in" " the result columns." msgstr "" -#: ../../build/doc/release_notes.rst:151 +#: ../../build/doc/release_notes.rst:152 msgid "Added departure field and location_id field in the result columns." msgstr "" -#: ../../build/doc/release_notes.rst:154 +#: ../../build/doc/release_notes.rst:155 msgid "vrpRouting 0.2" msgstr "" -#: ../../build/doc/release_notes.rst:157 +#: ../../build/doc/release_notes.rst:158 msgid "New experimental functions" msgstr "" -#: ../../build/doc/release_notes.rst:167 +#: ../../build/doc/release_notes.rst:168 msgid "VRP" msgstr "" -#: ../../build/doc/release_notes.rst:169 +#: ../../build/doc/release_notes.rst:170 msgid "vrp_compatibleVehicles" msgstr "" -#: ../../build/doc/release_notes.rst:170 +#: ../../build/doc/release_notes.rst:171 msgid "vrp_optimize" msgstr "" -#: ../../build/doc/release_notes.rst:171 +#: ../../build/doc/release_notes.rst:172 msgid "vrp_pickDeliverAdd" msgstr "" -#: ../../build/doc/release_notes.rst:172 +#: ../../build/doc/release_notes.rst:173 msgid "vrp_pickDeliver" msgstr "" -#: ../../build/doc/release_notes.rst:173 +#: ../../build/doc/release_notes.rst:174 msgid "vrp_simulation" msgstr "" -#: ../../build/doc/release_notes.rst:174 +#: ../../build/doc/release_notes.rst:175 msgid "vrp_viewRoute" msgstr "" -#: ../../build/doc/release_notes.rst:177 +#: ../../build/doc/release_notes.rst:178 msgid "vrpRouting 0.1" msgstr "" -#: ../../build/doc/release_notes.rst:180 +#: ../../build/doc/release_notes.rst:181 msgid "Extraction tasks" msgstr "" -#: ../../build/doc/release_notes.rst:181 +#: ../../build/doc/release_notes.rst:182 msgid "Porting pgRouting's VRP functionality" msgstr "" -#: ../../build/doc/release_notes.rst:184 +#: ../../build/doc/release_notes.rst:185 msgid "New official functions" msgstr "" diff --git a/locale/pot/release_notes.pot b/locale/pot/release_notes.pot index afb81e5c2..3f311f15d 100644 --- a/locale/pot/release_notes.pot +++ b/locale/pot/release_notes.pot @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: vrpRouting v0.4.2\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2024-08-06 20:01+0000\n" +"POT-Creation-Date: 2024-08-10 18:38+0000\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME \n" "Language-Team: LANGUAGE \n" @@ -73,46 +73,50 @@ msgid "Moved sphinx doc from .c files .rst files" msgstr "" #: ../../build/doc/release_notes.rst:52 -msgid "removing prefix `pgr_` & addding `namespace vrprouting`" +msgid "Removing prefix `pgr_` & addding `namespace vrprouting`" msgstr "" -#: ../../build/doc/release_notes.rst:56 -msgid "Documentation queries" +#: ../../build/doc/release_notes.rst:53 +msgid "Separating implementation from header vroom.hpp" msgstr "" #: ../../build/doc/release_notes.rst:57 -msgid "Renamed to extension `.pg`" +msgid "Documentation queries" msgstr "" #: ../../build/doc/release_notes.rst:58 +msgid "Renamed to extension `.pg`" +msgstr "" + +#: ../../build/doc/release_notes.rst:59 msgid "Removed `doc-` and `doc-vrp_` suffixes on file names" msgstr "" -#: ../../build/doc/release_notes.rst:61 +#: ../../build/doc/release_notes.rst:62 msgid "vrpRouting 0.4.1 Release Notes" msgstr "" -#: ../../build/doc/release_notes.rst:63 +#: ../../build/doc/release_notes.rst:64 msgid "To see all issues & pull requests closed by this release see the `Git closed milestone for 0.4.1 `_ on Github." msgstr "" -#: ../../build/doc/release_notes.rst:69 +#: ../../build/doc/release_notes.rst:70 msgid "Modification on experimental functions" msgstr "" -#: ../../build/doc/release_notes.rst:70 +#: ../../build/doc/release_notes.rst:71 msgid "OR Tools" msgstr "" -#: ../../build/doc/release_notes.rst:72 +#: ../../build/doc/release_notes.rst:73 msgid "vrp_bin_packing" msgstr "" -#: ../../build/doc/release_notes.rst:73 +#: ../../build/doc/release_notes.rst:74 msgid "vrp_knapsack" msgstr "" -#: ../../build/doc/release_notes.rst:74 +#: ../../build/doc/release_notes.rst:75 msgid "vrp_multiple_knapsack" msgstr "" @@ -120,7 +124,7 @@ msgstr "" msgid "Support for or-tools v9.10.4067" msgstr "" -#: ../../build/doc/release_notes.rst:80 +#: ../../build/doc/release_notes.rst:81 msgid "vrp_oneDepot" msgstr "" @@ -132,17 +136,17 @@ msgstr "" msgid "Result columns changed" msgstr "" -#: ../../build/doc/release_notes.rst:87 +#: ../../build/doc/release_notes.rst:88 msgid "Removal of Boost on the build" msgstr "" -#: ../../build/doc/release_notes.rst:88 -#: ../../build/doc/release_notes.rst:186 +#: ../../build/doc/release_notes.rst:89 +#: ../../build/doc/release_notes.rst:187 msgid "vrp_full_version" msgstr "" -#: ../../build/doc/release_notes.rst:89 -#: ../../build/doc/release_notes.rst:185 +#: ../../build/doc/release_notes.rst:90 +#: ../../build/doc/release_notes.rst:186 msgid "vrp_version" msgstr "" @@ -150,201 +154,201 @@ msgstr "" msgid "Boost removed from the result columns" msgstr "" -#: ../../build/doc/release_notes.rst:96 +#: ../../build/doc/release_notes.rst:97 msgid "vrpRouting 0.4.0 Release Notes" msgstr "" -#: ../../build/doc/release_notes.rst:98 +#: ../../build/doc/release_notes.rst:99 msgid "To see all issues & pull requests closed by this release see the `Git closed milestone for 0.4.0 `_ on Github." msgstr "" -#: ../../build/doc/release_notes.rst:103 +#: ../../build/doc/release_notes.rst:104 msgid "Added support for VROOM 1.12.0 (`#34 `_)" msgstr "" -#: ../../build/doc/release_notes.rst:104 +#: ../../build/doc/release_notes.rst:105 msgid "No visible changes on user side with respect to signatures." msgstr "" -#: ../../build/doc/release_notes.rst:105 +#: ../../build/doc/release_notes.rst:106 msgid "Adjusted to VROOM v1.12.0 due to internal breaking changes:" msgstr "" -#: ../../build/doc/release_notes.rst:107 +#: ../../build/doc/release_notes.rst:108 msgid "Made changes according to new vroom::Input signature." msgstr "" -#: ../../build/doc/release_notes.rst:108 +#: ../../build/doc/release_notes.rst:109 msgid "CI changes to compile without routing support, with Position Independent Code." msgstr "" -#: ../../build/doc/release_notes.rst:109 +#: ../../build/doc/release_notes.rst:110 msgid "Removed support for VROOM 1.11.0" msgstr "" -#: ../../build/doc/release_notes.rst:112 +#: ../../build/doc/release_notes.rst:113 msgid "vrpRouting 0.3" msgstr "" -#: ../../build/doc/release_notes.rst:114 +#: ../../build/doc/release_notes.rst:115 msgid "To see all issues & pull requests closed by this release see the `Git closed milestone for 0.3.0 `_ on Github." msgstr "" -#: ../../build/doc/release_notes.rst:119 +#: ../../build/doc/release_notes.rst:120 msgid "Modification of experimental functions" msgstr "" -#: ../../build/doc/release_notes.rst:120 -#: ../../build/doc/release_notes.rst:158 +#: ../../build/doc/release_notes.rst:121 +#: ../../build/doc/release_notes.rst:159 msgid "VROOM" msgstr "" -#: ../../build/doc/release_notes.rst:122 -#: ../../build/doc/release_notes.rst:160 -msgid "vrp_vroom" -msgstr "" - #: ../../build/doc/release_notes.rst:123 #: ../../build/doc/release_notes.rst:161 -msgid "vrp_vroomJobs" +msgid "vrp_vroom" msgstr "" #: ../../build/doc/release_notes.rst:124 #: ../../build/doc/release_notes.rst:162 -msgid "vrp_vroomShipments" +msgid "vrp_vroomJobs" msgstr "" #: ../../build/doc/release_notes.rst:125 #: ../../build/doc/release_notes.rst:163 -msgid "vrp_vroomPlain" +msgid "vrp_vroomShipments" msgstr "" #: ../../build/doc/release_notes.rst:126 #: ../../build/doc/release_notes.rst:164 -msgid "vrp_vroomJobsPlain" +msgid "vrp_vroomPlain" msgstr "" #: ../../build/doc/release_notes.rst:127 #: ../../build/doc/release_notes.rst:165 +msgid "vrp_vroomJobsPlain" +msgstr "" + +#: ../../build/doc/release_notes.rst:128 +#: ../../build/doc/release_notes.rst:166 msgid "vrp_vroomShipmentsPlain" msgstr "" -#: ../../build/doc/release_notes.rst:130 +#: ../../build/doc/release_notes.rst:131 msgid "Added support for VROOM 1.11.0 (`#24 `_)" msgstr "" -#: ../../build/doc/release_notes.rst:131 +#: ../../build/doc/release_notes.rst:132 msgid "Added setup time in jobs and shipments to refine service time modeling." msgstr "" -#: ../../build/doc/release_notes.rst:132 +#: ../../build/doc/release_notes.rst:133 msgid "Added support for custom cost matrices, along with the duration matrix." msgstr "" -#: ../../build/doc/release_notes.rst:134 +#: ../../build/doc/release_notes.rst:135 msgid "Using start_id, end_id, duration, cost as matrix table columns." msgstr "" -#: ../../build/doc/release_notes.rst:135 +#: ../../build/doc/release_notes.rst:136 msgid "Added timeout and exploration_level parameters to vroom-category functions." msgstr "" -#: ../../build/doc/release_notes.rst:136 +#: ../../build/doc/release_notes.rst:137 msgid "Added max_tasks column in vehicles." msgstr "" -#: ../../build/doc/release_notes.rst:137 +#: ../../build/doc/release_notes.rst:138 msgid "Added tests for empty skills arrays." msgstr "" -#: ../../build/doc/release_notes.rst:138 +#: ../../build/doc/release_notes.rst:139 msgid "Added custom scaling logic for speed_factor." msgstr "" -#: ../../build/doc/release_notes.rst:139 +#: ../../build/doc/release_notes.rst:140 msgid "Modified parameter names to make the naming consistent." msgstr "" -#: ../../build/doc/release_notes.rst:142 +#: ../../build/doc/release_notes.rst:143 msgid "Fixes" msgstr "" -#: ../../build/doc/release_notes.rst:143 +#: ../../build/doc/release_notes.rst:144 msgid "Honor client cancel requests for vroom-category functions." msgstr "" -#: ../../build/doc/release_notes.rst:144 +#: ../../build/doc/release_notes.rst:145 msgid "Added more information in the inner query and result columns of VROOM category functions (`#26 `_, `#27 `_):" msgstr "" -#: ../../build/doc/release_notes.rst:147 +#: ../../build/doc/release_notes.rst:148 msgid "Summary row in the output, for each vehicle and for the complete problem." msgstr "" -#: ../../build/doc/release_notes.rst:148 +#: ../../build/doc/release_notes.rst:149 msgid "Uassigned rows in the output with vehicle_id = -1." msgstr "" -#: ../../build/doc/release_notes.rst:149 +#: ../../build/doc/release_notes.rst:150 msgid "Modified travel_time result column to return travel time between current and last step." msgstr "" -#: ../../build/doc/release_notes.rst:150 +#: ../../build/doc/release_notes.rst:151 msgid "Added data jsonb field in jobs, shipments, vehicles, breaks as well as in the result columns." msgstr "" -#: ../../build/doc/release_notes.rst:151 +#: ../../build/doc/release_notes.rst:152 msgid "Added departure field and location_id field in the result columns." msgstr "" -#: ../../build/doc/release_notes.rst:154 +#: ../../build/doc/release_notes.rst:155 msgid "vrpRouting 0.2" msgstr "" -#: ../../build/doc/release_notes.rst:157 +#: ../../build/doc/release_notes.rst:158 msgid "New experimental functions" msgstr "" -#: ../../build/doc/release_notes.rst:167 +#: ../../build/doc/release_notes.rst:168 msgid "VRP" msgstr "" -#: ../../build/doc/release_notes.rst:169 +#: ../../build/doc/release_notes.rst:170 msgid "vrp_compatibleVehicles" msgstr "" -#: ../../build/doc/release_notes.rst:170 +#: ../../build/doc/release_notes.rst:171 msgid "vrp_optimize" msgstr "" -#: ../../build/doc/release_notes.rst:171 +#: ../../build/doc/release_notes.rst:172 msgid "vrp_pickDeliverAdd" msgstr "" -#: ../../build/doc/release_notes.rst:172 +#: ../../build/doc/release_notes.rst:173 msgid "vrp_pickDeliver" msgstr "" -#: ../../build/doc/release_notes.rst:173 +#: ../../build/doc/release_notes.rst:174 msgid "vrp_simulation" msgstr "" -#: ../../build/doc/release_notes.rst:174 +#: ../../build/doc/release_notes.rst:175 msgid "vrp_viewRoute" msgstr "" -#: ../../build/doc/release_notes.rst:177 +#: ../../build/doc/release_notes.rst:178 msgid "vrpRouting 0.1" msgstr "" -#: ../../build/doc/release_notes.rst:180 +#: ../../build/doc/release_notes.rst:181 msgid "Extraction tasks" msgstr "" -#: ../../build/doc/release_notes.rst:181 +#: ../../build/doc/release_notes.rst:182 msgid "Porting pgRouting's VRP functionality" msgstr "" -#: ../../build/doc/release_notes.rst:184 +#: ../../build/doc/release_notes.rst:185 msgid "New official functions" msgstr "" diff --git a/src/problem/CMakeLists.txt b/src/problem/CMakeLists.txt index 4914c4795..5d215dc02 100644 --- a/src/problem/CMakeLists.txt +++ b/src/problem/CMakeLists.txt @@ -8,4 +8,5 @@ ADD_LIBRARY(problem OBJECT fleet.cpp vehicle_node.cpp solution.cpp + vroom.cpp ) diff --git a/src/problem/vroom.cpp b/src/problem/vroom.cpp new file mode 100644 index 000000000..55f08ba59 --- /dev/null +++ b/src/problem/vroom.cpp @@ -0,0 +1,527 @@ +/*PGR-GNU***************************************************************** +File: vroom.cpp + +Copyright (c) 2021 pgRouting developers +Mail: project@pgrouting.org + +Function's developer: +Copyright (c) 2021 Ashish Kumar +Mail: ashishkr23438@gmail.com +------ + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + + ********************************************************************PGR-GNU*/ + +#include "vroom/vroom.hpp" + +#include +#include +#include + +#include +#include +#include +#include +#include + + +#include "c_types/vroom_rt.h" +#include "cpp_common/matrix_cell_t.hpp" +#include "cpp_common/vroom_break_t.hpp" +#include "cpp_common/vroom_job_t.hpp" +#include "cpp_common/vroom_shipment_t.hpp" +#include "cpp_common/vroom_time_window_t.hpp" +#include "cpp_common/vroom_vehicle_t.hpp" + +#include "cpp_common/base_matrix.hpp" +#include "cpp_common/interruption.hpp" +#include "cpp_common/messages.hpp" + +namespace vrprouting { +namespace problem { + +std::vector +Vroom::get_vroom_time_windows(const std::vector &time_windows) const { + std::vector tws; + for (auto time_window : time_windows) { + tws.push_back(vroom::TimeWindow(time_window.tw_open, time_window.tw_close)); + } + return !tws.empty() ? + tws + : std::vector(1, vroom::TimeWindow()); +} + +vroom::Amount +Vroom::get_vroom_amounts(const std::vector &amounts) const { + vroom::Amount amt; + if (!amounts.empty()) { + for (auto amount : amounts) { + amt.push_back(amount); + } + } else { + const unsigned int amount_size = m_vehicles.size() ? + static_cast(m_vehicles[0].capacity.size()) : 0; + // Default to zero amount with provided size. + amt = vroom::Amount(amount_size); + } + return amt; +} + +vroom::Amount +Vroom::get_vroom_amounts(const Amount *amounts, size_t count) const { + return get_vroom_amounts(std::vector(amounts, amounts + count)); +} + +vroom::Skills +Vroom::get_vroom_skills(const Skill *skills, size_t count) const { + return std::unordered_set (skills, skills + count); +} + +vroom::Job +Vroom::get_vroom_job( + const Vroom_job_t &job, + const std::vector &job_tws) const { + auto delivery = get_vroom_amounts(job.delivery, job.delivery_size); + auto pickup = get_vroom_amounts(job.pickup, job.pickup_size); + auto skills = get_vroom_skills(job.skills, job.skills_size); + auto time_windows = get_vroom_time_windows(job_tws); + auto location_id = static_cast(m_matrix.get_index(job.location_id)); + return vroom::Job( + job.id, location_id, job.setup, job.service, + delivery, pickup, skills, job.priority, + time_windows, job.data); +} + +/* + * param[in] jobs The vector container of Vroom_job_t + * param[in] jobs_tws The vector container of Vroom_time_window_t + */ +void +Vroom::add_jobs( + const std::vector &jobs, + const std::vector &jobs_tws) { + std::map> job_tws_map; + for (auto job_tw : jobs_tws) { + Idx id = job_tw.id; + if (job_tws_map.find(id) == job_tws_map.end()) { + job_tws_map[id] = std::vector(); + } + job_tws_map[id].push_back(job_tw); + } + for (auto job : jobs) { + m_jobs.push_back(get_vroom_job(job, job_tws_map[job.id])); + } +} + +void +Vroom::add_jobs(const Vroom_job_t *jobs, size_t count, + const Vroom_time_window_t *jobs_tws, size_t total_jobs_tws) { + add_jobs( + std::vector(jobs, jobs + count), + std::vector(jobs_tws, jobs_tws + total_jobs_tws)); +} + +std::pair +Vroom::get_vroom_shipment( + const Vroom_shipment_t &shipment, + const std::vector &pickup_tws, + const std::vector &delivery_tws) const { + auto amount = get_vroom_amounts(shipment.amount, shipment.amount_size); + auto skills = get_vroom_skills(shipment.skills, shipment.skills_size); + auto p_time_windows = get_vroom_time_windows(pickup_tws); + auto d_time_windows = get_vroom_time_windows(delivery_tws); + auto p_location_id = static_cast(m_matrix.get_index(shipment.p_location_id)); + auto d_location_id = static_cast(m_matrix.get_index(shipment.d_location_id)); + vroom::Job pickup = vroom::Job( + shipment.id, vroom::JOB_TYPE::PICKUP, p_location_id, + shipment.p_setup, shipment.p_service, amount, + skills, shipment.priority, p_time_windows, shipment.p_data); + vroom::Job delivery = vroom::Job( + shipment.id, vroom::JOB_TYPE::DELIVERY, d_location_id, + shipment.d_setup, shipment.d_service, amount, + skills, shipment.priority, d_time_windows, shipment.d_data); + return std::make_pair(pickup, delivery); +} + +/* + * param[in] shipments The vector container of Vroom_shipment_t + * param[in] shipments_tws Shipments time windows. The vector container of Vroom_time_window_t + */ +void +Vroom::add_shipments( + const std::vector &shipments, + const std::vector &shipments_tws) { + std::map> pickup_tws_map; + std::map> delivery_tws_map; + for (auto shipment_tw : shipments_tws) { + Idx id = shipment_tw.id; + if (shipment_tw.kind == 'p') { + if (pickup_tws_map.find(id) == pickup_tws_map.end()) { + pickup_tws_map[id] = std::vector(); + } + pickup_tws_map[id].push_back(shipment_tw); + } else if (shipment_tw.kind == 'd') { + if (delivery_tws_map.find(id) == delivery_tws_map.end()) { + delivery_tws_map[id] = std::vector(); + } + delivery_tws_map[id].push_back(shipment_tw); + } + } + for (auto shipment : shipments) { + m_shipments.push_back(get_vroom_shipment(shipment, pickup_tws_map[shipment.id], delivery_tws_map[shipment.id])); + } +} + +void +Vroom::add_shipments( + const Vroom_shipment_t *shipments, size_t count, + const Vroom_time_window_t *shipment_tws, size_t total_shipment_tws) { + add_shipments( + std::vector(shipments, shipments + count), + std::vector(shipment_tws, shipment_tws + total_shipment_tws)); +} + +std::vector +Vroom::get_vroom_breaks( + const std::vector &breaks, + const std::vector &breaks_tws) const { + std::map> breaks_tws_map; + for (const auto &break_tw : breaks_tws) { + Idx id = break_tw.id; + if (breaks_tws_map.find(id) == breaks_tws_map.end()) { + breaks_tws_map[id] = std::vector(); + } + breaks_tws_map[id].push_back(break_tw); + } + std::vector v_breaks; + for (const auto &v_break : breaks) { + v_breaks.push_back( + vroom::Break( + v_break.id, get_vroom_time_windows(breaks_tws_map[v_break.id]), v_break.service, v_break.data)); + } + return v_breaks; +} + +vroom::Vehicle +Vroom::get_vroom_vehicle( + const Vroom_vehicle_t &vehicle, + const std::vector &breaks, + const std::vector &breaks_tws) const { + auto capacity = get_vroom_amounts(vehicle.capacity, vehicle.capacity_size); + auto skills = get_vroom_skills(vehicle.skills, vehicle.skills_size); + auto time_window = vroom::TimeWindow(vehicle.tw_open, vehicle.tw_close); + auto v_breaks = get_vroom_breaks(breaks, breaks_tws); + + std::optional start_id; + std::optional end_id; + // Set the value of start or end index only if they are present + if (vehicle.start_id != -1) { + start_id = static_cast(m_matrix.get_index(vehicle.start_id)); + } + if (vehicle.end_id != -1) { + end_id = static_cast(m_matrix.get_index(vehicle.end_id)); + } + return vroom::Vehicle(vehicle.id, start_id, end_id, + vroom::DEFAULT_PROFILE, capacity, skills, time_window, + v_breaks, vehicle.data, vehicle.speed_factor, + static_cast(vehicle.max_tasks)); +} + +/* + * param[in] vehicles The vector container of Vroom_vehicle_t + * param[in] breaks Vehicle breaks. The vector container of Vroom_break_t + * param[in] breaks_tws_map Vehicle breaks time windows. The vector container of Vroom_time_window_t + */ +void +Vroom::add_vehicles( + const std::vector &vehicles, + const std::vector &breaks, + const std::vector &breaks_tws) { + std::map> breaks_tws_map; + for (auto break_tw : breaks_tws) { + Idx id = break_tw.id; + if (breaks_tws_map.find(id) == breaks_tws_map.end()) { + breaks_tws_map[id] = std::vector(); + } + breaks_tws_map[id].push_back(break_tw); + } + + std::map> v_breaks_map; + for (auto v_break : breaks) { + Idx v_id = v_break.vehicle_id; + if (v_breaks_map.find(v_id) == v_breaks_map.end()) { + v_breaks_map[v_id] = std::vector(); + } + v_breaks_map[v_id].push_back(v_break); + } + + for (auto vehicle : vehicles) { + std::vector v_breaks = v_breaks_map[vehicle.id]; + std::vector v_breaks_tws; + for (auto v_break : v_breaks) { + std::vector tws = breaks_tws_map[v_break.id]; + v_breaks_tws.insert(v_breaks_tws.end(), tws.begin(), tws.end()); + } + m_vehicles.push_back(get_vroom_vehicle(vehicle, v_breaks, v_breaks_tws)); + } +} + +void +Vroom::add_vehicles(const Vroom_vehicle_t *vehicles, size_t count, + const Vroom_break_t *breaks, size_t total_breaks, + const Vroom_time_window_t *breaks_tws, size_t total_breaks_tws) { + add_vehicles(std::vector(vehicles, vehicles + count), + std::vector(breaks, breaks + total_breaks), + std::vector(breaks_tws, breaks_tws + total_breaks_tws)); +} + +/* + * param[in] matrix The matrix + */ +void +Vroom::add_matrix(const vrprouting::base::Base_Matrix &matrix) { + m_matrix = matrix; +} + +void +Vroom::get_amount(vroom::Amount vroom_amount, Amount **amount) { + size_t amount_size = vroom_amount.size(); + for (size_t i = 0; i < amount_size; i++) { + *((*amount) + i) = vroom_amount[i]; + } +} + +StepType +Vroom::get_job_step_type(vroom::JOB_TYPE vroom_job_type) { + StepType step_type; + switch (vroom_job_type) { + case vroom::JOB_TYPE::SINGLE: + step_type = 2; + break; + case vroom::JOB_TYPE::PICKUP: + step_type = 3; + break; + case vroom::JOB_TYPE::DELIVERY: + step_type = 4; + break; + } + return step_type; +} + +StepType +Vroom::get_step_type(vroom::Step step) { + StepType step_type = 0; + switch (step.step_type) { + case vroom::STEP_TYPE::START: + step_type = 1; + break; + case vroom::STEP_TYPE::END: + step_type = 6; + break; + case vroom::STEP_TYPE::BREAK: + step_type = 5; + break; + case vroom::STEP_TYPE::JOB: + step_type = get_job_step_type(step.job_type); + break; + } + return step_type; +} + +std::vector +Vroom::get_results(vroom::Solution solution) { + std::vector results; + std::vector routes = solution.routes; + Idx vehicle_seq = 1; + char *empty_desc = strdup("{}"); + for (auto route : routes) { + Idx step_seq = 1; + Duration prev_duration = 0; + char *vehicle_data = strdup(route.description.c_str()); + for (auto step : route.steps) { + Idx task_id = step.id; + MatrixIndex location_id = m_matrix.get_original_id(step.location.index()); + char *task_data = strdup(step.description.c_str()); + StepType step_type = get_step_type(step); + if (step_type == 1 || step_type == 6) { + task_id = static_cast(-1); + task_data = empty_desc; + } + + size_t load_size = step.load.size(); + Amount *load = reinterpret_cast(malloc(load_size * sizeof(Amount))); + get_amount(step.load, &load); + + Duration travel_time = step.duration - prev_duration; + prev_duration = step.duration; + Duration departure = step.arrival + step.setup + step.service + step.waiting_time; + results.push_back({ + vehicle_seq, // vehicles_seq + route.vehicle, // vehicles_id + vehicle_data, // vehicle_data + step_seq, // step_seq + step_type, // step_type + task_id, // task_id + location_id, // location_id + task_data, // task_data + step.arrival, // arrival + travel_time, // travel_time + step.setup, // setup_time + step.service, // service_time + step.waiting_time, // waiting_time + departure, // departure + load, // load + load_size // load size + }); + step_seq++; + } + // The summary of this route + Idx task_id = 0; + results.push_back({ + vehicle_seq, // vehicles_seq + route.vehicle, // vehicles_id + vehicle_data, // vehicle_data + 0, // step_seq = 0 for route summary + 0, // step_type = 0 for route summary + task_id, // task_id = 0 for route summary + 0, // location_id = 0 for route summary + empty_desc, // task_data + 0, // No arrival time + route.duration, // Total travel time + route.setup, // Total setup time + route.service, // Total service time + route.waiting_time, // Total waiting time + 0, // No departure time + {}, // load + 0 // load size + }); + vehicle_seq++; + } + + std::vector unassigned = solution.unassigned; + Idx step_seq = 1; + for (auto job : unassigned) { + StepType job_step = get_job_step_type(job.type); + Idx vehicle_id = static_cast(-1); + Idx job_id = job.id; + auto location_id = m_matrix.get_original_id(job.location.index()); + char *task_data = strdup(job.description.c_str()); + results.push_back({ + vehicle_seq, // vehicles_seq + vehicle_id, // vehicles_id = -1 for unassigned jobs + empty_desc, // vehicle_data + step_seq, // step_seq + job_step, // step_type + job_id, // task_id + location_id, // location_id + task_data, // task_data + 0, // No arrival time + 0, // No travel_time + 0, // No setup_time + 0, // No service_time + 0, // No waiting_time + 0, // No departure time + {}, // load + 0 // load size + }); + step_seq++; + } + + // The summary of the entire problem + vroom::Summary summary = solution.summary; + Idx vehicle_id = 0; + Idx job_id = 0; + results.push_back({ + 0, // vehicles_seq = 0 for problem summary + vehicle_id, // vehicles_id = 0 for problem summary + empty_desc, // vehicle_data + 0, // step_seq = 0 for problem summary + 0, // step_type = 0 for problem summary + job_id, // task_id = 0 for problem summary + 0, // location_id = 0 for problem summary + empty_desc, // task_data + 0, // No arrival time + summary.duration, // Total travel time + summary.setup, // Total setup time + summary.service, // Total service time + summary.waiting_time, // Total waiting time + 0, // No departure time + {}, // load + 0 // load size + }); + return results; +} + +/* + * param[in] exploration_level + * param[in] timeout + * param[in] loading_timex + * + * @returns The vroom results. A vector of Vroom_rt + */ +std::vector +Vroom::solve( + int32_t exploration_level, + int32_t timeout, + int32_t loading_time) { + std::vector results; + + /* abort in case an interruption occurs (e.g. the query is being cancelled) */ + CHECK_FOR_INTERRUPTS(); + try { + const unsigned int amount_size = m_vehicles.size() ? + static_cast(m_vehicles[0].capacity.size()) + : 0; + vroom::Input problem_instance; + problem_instance.set_amount_size(amount_size); + + for (const auto &vehicle : m_vehicles) { + problem_instance.add_vehicle(vehicle); + } + for (const auto &job : m_jobs) { + problem_instance.add_job(job); + } + for (const auto &shipment : m_shipments) { + problem_instance.add_shipment(shipment.first, shipment.second); + } + vroom::Matrix duration_matrix = m_matrix.get_vroom_duration_matrix(); + vroom::Matrix cost_matrix = m_matrix.get_vroom_cost_matrix(); + problem_instance.set_durations_matrix(vroom::DEFAULT_PROFILE, std::move(duration_matrix)); + problem_instance.set_costs_matrix(vroom::DEFAULT_PROFILE, std::move(cost_matrix)); + + unsigned threads = 4; + if (timeout < 0) { + auto solution = problem_instance.solve( + static_cast(exploration_level), threads); + results = get_results(solution); + } else { + int timeout_ms = (loading_time <= timeout * 1000) ? (timeout * 1000 - loading_time) : 0; + auto solution = problem_instance.solve( + static_cast(exploration_level), threads, timeout_ms); + results = get_results(solution); + } + } catch (const vroom::Exception &ex) { + throw; + } catch (const std::exception &ex) { + throw; + } catch (...) { + throw; + } + return results; +} + +} // namespace problem +} // namespace vrprouting diff --git a/src/vroom/vroom_driver.cpp b/src/vroom/vroom_driver.cpp index c9b40aa85..6a95b4807 100644 --- a/src/vroom/vroom_driver.cpp +++ b/src/vroom/vroom_driver.cpp @@ -34,9 +34,16 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. #include #include +#include "vroom/vroom.hpp" + +#include "c_types/vroom_rt.h" #include "cpp_common/alloc.hpp" #include "cpp_common/assert.hpp" -#include "vroom/vroom.hpp" +#include "cpp_common/identifiers.hpp" +#include "cpp_common/base_matrix.hpp" +#include "cpp_common/vroom_vehicle_t.hpp" +#include "cpp_common/vroom_shipment_t.hpp" +#include "cpp_common/vroom_job_t.hpp" /** @file vroom_driver.cpp * @brief Handles actual calling of function in the `vrp_vroom.hpp` file. @@ -196,7 +203,7 @@ do_vrp_vroom( return; } - vrprouting::Vrp_vroom_problem problem; + vrprouting::problem::Vroom problem; problem.add_matrix(matrix); problem.add_vehicles(vehicles, total_vehicles, breaks, total_breaks,