-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathRRT (Rapidly-Exploring Random Trees)
More file actions
116 lines (98 loc) · 3.3 KB
/
RRT (Rapidly-Exploring Random Trees)
File metadata and controls
116 lines (98 loc) · 3.3 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
#include <iostream>
#include <vector>
#include <cmath>
#include <random>
struct Point {
double x;
double y;
};
class Node {
public:
Point point;
int parent;
Node(Point p, int parentIdx) : point(p), parent(parentIdx) {}
};
class RRTPlanner {
public:
RRTPlanner(Point start, Point goal, double mapWidth, double mapHeight, int maxIterations, double stepSize)
: startNode(start, -1), goalNode(goal, -1), maxIterations(maxIterations), stepSize(stepSize),
mapWidth(mapWidth), mapHeight(mapHeight), randomGenerator(std::random_device()()) {
nodes.push_back(startNode);
}
double distance(const Point& p1, const Point& p2) {
return std::sqrt(std::pow(p2.x - p1.x, 2) + std::pow(p2.y - p1.y, 2));
}
Point generateRandomPoint() {
std::uniform_real_distribution<double> xDist(0, mapWidth);
std::uniform_real_distribution<double> yDist(0, mapHeight);
return {xDist(randomGenerator), yDist(randomGenerator)};
}
int nearestNeighbor(const Point& target) {
int nearestIdx = 0;
double nearestDist = distance(nodes[0].point, target);
for (int i = 1; i < nodes.size(); ++i) {
double dist = distance(nodes[i].point, target);
if (dist < nearestDist) {
nearestDist = dist;
nearestIdx = i;
}
}
return nearestIdx;
}
Point steer(const Point& from, const Point& to, double maxDistance) {
double dist = distance(from, to);
if (dist <= maxDistance) {
return to;
} else {
double ratio = maxDistance / dist;
double newX = from.x + (to.x - from.x) * ratio;
double newY = from.y + (to.y - from.y) * ratio;
return {newX, newY};
}
}
void extendTree() {
Point randomPoint = generateRandomPoint();
int nearestIdx = nearestNeighbor(randomPoint);
Point nearestPoint = nodes[nearestIdx].point;
Point newPoint = steer(nearestPoint, randomPoint, stepSize);
// Check collision or validity of newPoint
nodes.push_back(Node(newPoint, nearestIdx));
}
std::vector<Point> plan() {
for (int i = 0; i < maxIterations; ++i) {
extendTree();
}
// Generate path from goal to start using parent pointers
std::vector<Point> path;
int currentNodeIdx = nodes.size() - 1;
while (currentNodeIdx != -1) {
path.push_back(nodes[currentNodeIdx].point);
currentNodeIdx = nodes[currentNodeIdx].parent;
}
return path;
}
private:
Node startNode;
Node goalNode;
int maxIterations;
double stepSize;
double mapWidth;
double mapHeight;
std::vector<Node> nodes;
std::default_random_engine randomGenerator;
};
int main() {
Point start = {10, 10};
Point goal = {90, 90};
double mapWidth = 100;
double mapHeight = 100;
int maxIterations = 1000;
double stepSize = 5.0;
RRTPlanner planner(start, goal, mapWidth, mapHeight, maxIterations, stepSize);
std::vector<Point> path = planner.plan();
// Print the path
for (int i = path.size() - 1; i >= 0; --i) {
std::cout << "Step " << path.size() - i << ": (" << path[i].x << ", " << path[i].y << ")\n";
}
return 0;
}