2 * SPDX-FileCopyrightText: 2021 Jiri Vlasak <jiri.vlasak.2@cvut.cz>
4 * SPDX-License-Identifier: GPL-3.0-only
7 /*! \brief RRT* extensions.
9 * The extensions are used to implement or change the default behavior of the
13 * \defgroup ext-col Collision detection extensions
14 * \defgroup ext-store Node storage and searching tree extensions
15 * \defgroup ext-cost Cost extensions
16 * \defgroup ext-opt Path optimization extensions
17 * \defgroup ext-sampl Random sampling extensions
18 * \defgroup ext-steer Steering procedure extensions
19 * \defgroup ext-aux Auxilliary extensions
30 #define GRID 1 // in meters
31 #define GRID_WIDTH 40 // in meters
32 #define GRID_HEIGHT 40 // in meters
33 #define GRID_MAX_XI ((unsigned int) floor(GRID_WIDTH / GRID)) // min is 0
34 #define GRID_MAX_YI ((unsigned int) floor(GRID_HEIGHT / GRID)) // min is 0
37 #define GRID_MAX_HI 60
41 /*! \brief Collision check based on occupancy grid.
45 class RRTExt20 : public virtual RRTS {
47 std::vector<bcar::Point> const *_points_to_check = nullptr;
48 bool collide_steered();
50 void set_points_to_check(std::vector<bcar::Point> const *p);
53 /*! \brief Use Dubins paths-based steering procedure.
56 * \see https://github.com/AndrewWalker/Dubins-Curves
58 class RRTExt19 : public virtual RRTS {
60 void steer(RRTNode const &f, RRTNode const &t);
63 /*! \brief Finish when more than 1000 iterations.
67 class RRTExt18 : public virtual RRTS {
69 bool should_finish() const;
72 /*! \brief Finish when goal found or more than 1000 iterations.
76 class RRTExt17 : public virtual RRTS {
78 bool should_finish() const;
81 /*! \brief Use Reeds & Shepp steering procedure.
85 class RRTExt16 : public virtual RRTS {
87 void steer(RRTNode const& f, RRTNode const& t);
90 /*! \brief Log goal's cumulative cost each iteration.
94 class RRTExt15 : public virtual RRTS {
96 std::vector<double> log_path_cost_;
98 Json::Value json() const;
99 void json(Json::Value jvi);
103 /*! \brief Random sampling in the circuit between root and goal.
106 * \see https://stackoverflow.com/questions/5837572/generate-a-random-point-within-a-circle-uniformly/50746409#50746409
108 class RRTExt14 : public virtual RRTS {
111 double circle_r_ = 0.0;
112 std::uniform_real_distribution<double> udr_;
113 std::uniform_real_distribution<double> udt_;
114 std::uniform_real_distribution<double> udh_;
121 /*! \brief Use Dijkstra algorithm to find path between interesting nodes.
123 * The search for interesting nodes starts at root, the last drivable nodes is
124 * added to interesting nodes until goal is reached.
128 class RRTExt13 : public virtual RRTS {
132 RRTNode* node = nullptr;
137 DijkstraNode(RRTNode* n);
139 class DijkstraNodeComparator {
141 int operator() (DijkstraNode const& n1, DijkstraNode const& n2);
143 class DijkstraNodeBackwardComparator {
145 int operator() (DijkstraNode const& n1, DijkstraNode const& n2);
147 std::vector<RRTNode*> opath_;
148 double ogoal_cc_ = 0.0;
150 std::vector<DijkstraNode> dn_;
151 void interesting_forward();
152 void interesting_backward();
153 void dijkstra_forward();
154 void dijkstra_backward();
158 Json::Value json() const;
159 void json(Json::Value jvi);
163 /* \brief Different `steer` procedures.
165 Use sampling in control input for `steer1`. Use R&S steering for `steer2`.
167 class RRTExt12 : public virtual RRTS {
169 void steer1(RRTNode &f, RRTNode &t);
178 class RRTExt11 : public virtual RRTS {
180 bool goal_found(RRTNode &f);
183 /*! \brief Reeds & Shepp (build) and Euclidean + abs angle (search).
185 * Use Reeds & Shepp path length for building tree data structure and Euclidean
186 * distance + (abs) heading difference + 0.1 * backward-forward direction
187 * changes for searching it.
190 * \see https://doi.org/10.1109/TITS.2015.2477355
192 class RRTExt10 : public virtual RRTS {
194 double cost_build(RRTNode const& f, RRTNode const& t) const;
195 double cost_search(RRTNode const& f, RRTNode const& t) const;
198 /* \brief Use grid data structure to store RRT nodes.
200 This approach speeds up the search process for the nearest neighbor and
201 the near vertices procedures.
203 class RRTExt9 : public virtual RRTS {
207 bool changed_ = false;
208 std::vector<RRTNode *> nodes_;
210 void nn(RRTNode *t, RRTNode **nn, RRTS *p);
211 void store_node(RRTNode *n);
216 return this->changed_;
218 std::vector<RRTNode *> &nodes()
225 Cell grid_[GRID_MAX_XI][GRID_MAX_YI][GRID_MAX_HI];
231 double h_max_ = 2 * M_PI;
233 unsigned int xi(RRTNode n);
234 unsigned int yi(RRTNode n);
235 unsigned int hi(RRTNode n);
239 void store_node(RRTNode n);
240 RRTNode *nn(RRTNode &t);
241 std::vector<RRTNode *> nv(RRTNode &t);
244 /*! \brief Use 3D k-d tree data structure to store RRT nodes.
246 * This approach speeds up the search process for the nearest neighbor and the
247 * near vertices procedures. This extension implements 3D K-d tree.
250 * \see https://en.wikipedia.org/wiki/K-d_tree
252 class RRTExt8 : public virtual RRTS {
256 RRTNode* node = nullptr;
257 KdNode* left = nullptr;
258 KdNode* right = nullptr;
261 KdNode* kdroot_ = nullptr;
262 std::vector<KdNode> kdnodes_;
263 void store(RRTNode* n, KdNode*& ref, unsigned int lvl);
264 void find_nn(RRTNode const& t, KdNode const* const r, unsigned int lvl);
265 void find_nv(RRTNode const& t, KdNode const* const r, unsigned int lvl);
269 void store(RRTNode n);
270 void find_nn(RRTNode const& t);
271 void find_nv(RRTNode const& t);
274 /* \brief Use k-d tree data structure to store RRT nodes.
276 This approach speeds up the search process for the nearest neighbor and
277 the near vertices procedures. This extension implements 2D K-d tree.
279 \see https://en.wikipedia.org/wiki/K-d_tree
281 class RRTExt7 : public virtual RRTS {
285 RRTNode *node_ = nullptr;
286 KdNode *left_ = nullptr;
287 KdNode *right_ = nullptr;
290 RRTNode *node() const { return this->node_; }
291 KdNode *&left() { return this->left_; }
292 KdNode *&right() { return this->right_; }
295 KdNode *kdroot_ = nullptr;
296 void delete_kd_nodes(KdNode *n);
297 void store_node(RRTNode *n, KdNode *&r, int l);
298 void nn(RRTNode *&n, RRTNode &t, KdNode *r, int l, double &d);
302 void store_node(RRTNode n);
303 RRTNode *nn(RRTNode &t);
304 std::vector<RRTNode *> nv(RRTNode &t);
307 /*! \brief Reeds & Shepp (build, search).
309 * Use Reeds & Shepp path length for building tree data structure as well as for
314 class RRTExt6 : public virtual RRTS {
316 double cost_build(RRTNode const& f, RRTNode const& t) const;
317 double cost_search(RRTNode const& f, RRTNode const& t) const;
320 /* \brief Different costs extension.
322 Use different cost for bulding tree data structure and searching in the
323 structure. This one is complementary to `rrtext1.cc`.
325 class RRTExt5 : public virtual RRTS {
327 /* \brief Reeds and Shepp path length.
329 double cost_build(RRTNode &f, RRTNode &t);
330 /* \brief Euclidean distance.
332 double cost_search(RRTNode &f, RRTNode &t);
335 /* \brief Use grid data structure to store RRT nodes.
337 This approach speeds up the search process for the nearest neighbor and
338 the near vertices procedures.
340 class RRTExt4 : public virtual RRTS {
344 bool changed_ = false;
345 std::vector<RRTNode *> nodes_;
347 void nn(RRTNode *t, RRTNode **nn, RRTS *p);
348 void store_node(RRTNode *n);
353 return this->changed_;
355 std::vector<RRTNode *> &nodes()
362 Cell grid_[GRID_MAX_XI][GRID_MAX_YI]; // [0, 0] is bottom left
368 unsigned int xi(RRTNode n);
369 unsigned int yi(RRTNode n);
373 void store_node(RRTNode n);
374 RRTNode *nn(RRTNode &t);
375 std::vector<RRTNode *> nv(RRTNode &t);
378 /* \brief Use Dijkstra algorithm to find the shorter path.
380 class RRTExt3 : public virtual RRTS {
384 std::vector<RRTNode *> orig_path_;
385 double orig_path_cost_ = 9999;
386 std::vector<RRTNode *> first_optimized_path_;
387 double first_optimized_path_cost_ = 9999;
388 void first_path_optimization();
389 void second_path_optimization();
392 void json(Json::Value jvi);
395 std::vector<RRTNode *> &orig_path()
397 return this->orig_path_;
399 double &orig_path_cost() { return this->orig_path_cost_; }
400 void orig_path_cost(double c) { this->orig_path_cost_ = c; }
401 std::vector<RRTNode *> &first_optimized_path()
403 return this->first_optimized_path_;
405 double &first_optimized_path_cost() {
406 return this->first_optimized_path_cost_;
408 void first_optimized_path_cost(double c) {
409 this->first_optimized_path_cost_ = c;
413 /*! \brief Use cute_c2 library for collision detection.
416 * \see https://github.com/RandyGaul/cute_headers/blob/master/cute_c2.h
418 class RRTExt2 : public virtual RRTS {
422 std::vector<c2Poly> c2_obstacles_;
423 bool collide(RRTNode const& n);
424 bool collide_steered();
427 Json::Value json() const;
428 void json(Json::Value jvi);
432 /* \brief Different costs extension.
434 Use different cost for bulding tree data structure and searching in the
437 class RRTExt1 : public virtual RRTS {
439 /* \brief Reeds and Shepp path length.
441 double cost_build(RRTNode &f, RRTNode &t);
442 /* \brief Matej's heuristics.
444 double cost_search(RRTNode &f, RRTNode &t);
448 #endif /* RRTS_RRTEXT_H */