From b660b8f1530bd8615eee691219e52d542a2e232e Mon Sep 17 00:00:00 2001 From: Tibor Bizjak Date: Wed, 26 Jul 2023 14:17:04 +0200 Subject: [PATCH] chapter 03 exercise partial solution --- udemy-cpp/exc01/AdConstants.h | 4 +- udemy-cpp/exc01/AdFunctions.cc | 116 +++++++++++++++++++++++++++++++-- udemy-cpp/exc01/AdFunctions.h | 12 +++- udemy-cpp/exc01/AdTypes.h | 10 ++- udemy-cpp/exc01/main.cc | 7 ++ 5 files changed, 140 insertions(+), 9 deletions(-) diff --git a/udemy-cpp/exc01/AdConstants.h b/udemy-cpp/exc01/AdConstants.h index bf81707..b4c6252 100644 --- a/udemy-cpp/exc01/AdConstants.h +++ b/udemy-cpp/exc01/AdConstants.h @@ -5,10 +5,12 @@ namespace Ad { -namespace Constants +namespace Consts { constexpr std::int32_t EGO_VEHICLE_ID = -1; +constexpr std::size_t VEHICLES_PER_LANE = 2; +constexpr std::int8_t VISUALIZE_STEP = 20; } // namespace Constants } // namespace Ad diff --git a/udemy-cpp/exc01/AdFunctions.cc b/udemy-cpp/exc01/AdFunctions.cc index 74391e7..76b7e3d 100644 --- a/udemy-cpp/exc01/AdFunctions.cc +++ b/udemy-cpp/exc01/AdFunctions.cc @@ -1,6 +1,8 @@ #include #include #include +#include +#include #include "AdConstants.h" #include "AdFunctions.h" @@ -10,6 +12,7 @@ namespace Ad namespace Utils { +/* kph_to_mps: converts kmph to meters/second */ constexpr float kph_to_mps(const float kph) { return 0.2778 * kph; @@ -20,26 +23,131 @@ constexpr float kph_to_mps(const float kph) namespace Data { +/* init_ego_vehicle: initializes ego vehicle */ Types::Vehicle init_ego_vehicle() { return Types::Vehicle{ - .id = Constants::EGO_VEHICLE_ID, + .id = Consts::EGO_VEHICLE_ID, .lane = Types::Lane::Center, .speed_mps = Utils::kph_to_mps(135), - .rel_distance_m = 0, + .rel_dist_m = 0, }; } +/* init_vehicle_array: initialize an array of vehicles */ +template +static void init_vehicle_array(std::array &arr, int32_t start_id, Types::Lane lane) +{ + /* init random generators */ + std::mt19937 rng(std::random_device{}()); + std::uniform_real_distribution speed(-150, 150); + std::uniform_real_distribution dist_gen(0, Consts::VISUALIZE_STEP); + + double dist = static_cast (-Consts::VISUALIZE_STEP) * (arr.size() / 2 + 1); + + for (int32_t i = 0; i < arr.size(); i++) + arr[i] = Types::Vehicle{ + .id = start_id++, + .lane = lane, + .speed_mps = Utils::kph_to_mps(speed(rng)), + .rel_dist_m = (dist += Consts::VISUALIZE_STEP + dist_gen(rng)) + }; +} + +/* init_vehicles: initializes vehicles */ +Types::NeighborVehicles init_vehicles() +{ + auto nv = Types::NeighborVehicles{}; + + int32_t id = 0; + init_vehicle_array(nv.left_lane, id, Types::Lane::Left); + init_vehicle_array(nv.center_lane, (id += nv.left_lane.size()), Types::Lane::Center); + init_vehicle_array(nv.right_lane, (id += nv.right_lane.size()), Types::Lane::Right); + + return nv; +} + + + } // namespace Ad::Data namespace Visualize { -void print_vehicle(const Types::Vehicle vehicle) +/* print_lane: prints lane, helper function for print vehicle */ +void print_lane(const Types::Lane lane) +{ + #define if_lane(LANE) if (lane == Types::Lane::LANE) std::cout << #LANE; else + if_lane(Left) + if_lane(Center) + if_lane(Right) + /* else */ + std::cout << "Unknown"; +} + +/* print_vehicle: prints vehicle */ +void print_vehicle(const Types::Vehicle &vehicle) { std::cout << "Vehicle " << vehicle.id << '\n'; + std::cout << "Lane : "; + print_lane(vehicle.lane); + std::cout << '\n'; std::cout << "speed : " << vehicle.speed_mps << " m/s\n"; - std::cout << "distance : " << vehicle.rel_distance_m << " m\n"; + std::cout << "distance : " << vehicle.rel_dist_m << " m\n"; +} + +/* print_vehicle_array: helper function for print_neghbor_vehicles */ +template +static void print_vehicle_array(const std::array &arr) +{ + for (int32_t i = 0; i < arr.size(); i++) { + print_vehicle(arr[i]); + std::cout << '\n'; + } +} + +/* print_neghbor_vehicles: print neghbor vehicles information */ +void print_neighbor_vehicles(const Types::NeighborVehicles &vehicles) +{ + print_vehicle_array(vehicles.left_lane); + print_vehicle_array(vehicles.center_lane); + print_vehicle_array(vehicles.right_lane); +} + +/* print_scene: prints scene + * very rough implementation */ +void print_scene(const Types::Vehicle &ego_vehicle, + const Types::NeighborVehicles &vehicles) +{ + /* TODO : sort NeighborVehicles arrays */ + double min_dist_d = std::min({vehicles.left_lane[0].rel_dist_m, + vehicles.center_lane[0].rel_dist_m, + vehicles.right_lane[0].rel_dist_m}); + + double max_dist_d = std::max({vehicles.left_lane.back().rel_dist_m, + vehicles.center_lane.back().rel_dist_m, + vehicles.right_lane.back().rel_dist_m}); + + int32_t min_dist = std::floor(min_dist_d / Consts::VISUALIZE_STEP) * Consts::VISUALIZE_STEP; + int32_t max_dist = std::ceil(max_dist_d / Consts::VISUALIZE_STEP) * Consts::VISUALIZE_STEP; + + int32_t li, ci, ri, count; + li = ci = ri = Consts::VEHICLES_PER_LANE - 1; + std::cout << " L C R\n"; + for (int32_t dist = max_dist; dist >= min_dist; dist -= Consts::VISUALIZE_STEP) { + printf("%8d| ", dist); + char c; +#define HANDLE_LANE(lane, li) \ + for (count = 0; li >= 0 && vehicles.lane[li].rel_dist_m >= dist-Consts::VISUALIZE_STEP; count++, li--) \ + ; \ + c = !count ? ' ' : (count > 1) ? '0' + count : (vehicles.lane[li+1].speed_mps >= 0) ? 'v' : '^'; \ + std::cout << c << " | " + HANDLE_LANE(left_lane, li); + HANDLE_LANE(center_lane, ci); + HANDLE_LANE(right_lane, ri); + std::cout << '\n'; + } + } } // namespace Ad::Visualize diff --git a/udemy-cpp/exc01/AdFunctions.h b/udemy-cpp/exc01/AdFunctions.h index 9859ebe..5c4dcb8 100644 --- a/udemy-cpp/exc01/AdFunctions.h +++ b/udemy-cpp/exc01/AdFunctions.h @@ -11,12 +11,18 @@ namespace Utils namespace Data { - Types::Vehicle init_ego_vehicle(); + Types::Vehicle init_ego_vehicle(); + Types::NeighborVehicles init_vehicles(); } // namespace Ad::Data namespace Visualize { - void print_vehicle(const Types::Vehicle vehicle); -} // namespace Ad::Visualize + void print_vehicle(const Types::Vehicle &vehicle); + void print_neighbor_vehicles(const Types::NeighborVehicles &vehicles); + + void print_scene(const Types::Vehicle &ego_vehicle, + const Types::NeighborVehicles &vehicles); + +} // namespace Ad::Visualize } // namespace Ad diff --git a/udemy-cpp/exc01/AdTypes.h b/udemy-cpp/exc01/AdTypes.h index 26f184f..881a3e0 100644 --- a/udemy-cpp/exc01/AdTypes.h +++ b/udemy-cpp/exc01/AdTypes.h @@ -1,6 +1,7 @@ #pragma once #include +#include #include "AdConstants.h" @@ -22,7 +23,14 @@ struct Vehicle std::int32_t id; Lane lane; double speed_mps; - double rel_distance_m; + double rel_dist_m; +}; + +struct NeighborVehicles +{ + std::array left_lane; + std::array center_lane; + std::array right_lane; }; } // namespace Ad::Types diff --git a/udemy-cpp/exc01/main.cc b/udemy-cpp/exc01/main.cc index 1064b92..0ee85b3 100644 --- a/udemy-cpp/exc01/main.cc +++ b/udemy-cpp/exc01/main.cc @@ -8,7 +8,14 @@ int main() { auto ego_vehicle = Ad::Data::init_ego_vehicle(); + auto vehicles = Ad::Data::init_vehicles(); + Ad::Visualize::print_vehicle(ego_vehicle); + std::cout << '\n'; + + Ad::Visualize::print_neighbor_vehicles(vehicles); + + Ad::Visualize::print_scene(ego_vehicle, vehicles); return 0; }