赞
踩
大佬博主博客:图解自动驾驶中的运动规划(Motion Planning),附几十种规划算法_自动驾驶驾驶动态规划算法-CSDN博客
参考文献:
[1]https://ieeexplore.ieee.org/document/736775
[2]https://ieeexplore.ieee.org/document/1690266
- #include<cstdio>
- #include<cstring>
- #include<algorithm>
- #include<iostream>
- #define Inf 0x3f3f3f3f
-
- using namespace std;
-
- int map[1005][1005];
-
- int vis[1005], dis[1005];
- int n, m;
- void Init()
- {
- memset(map, Inf, sizeof(map));
- for (int i = 1; i <= n; i++)
- {
- map[i][i] = 0;
- }
- }
-
- void Getmap()
- {
- int u, v, w;
- for (int t = 1; t <= m; t++)
- {
- scanf_s("%d%d%d", &u, &v, &w);
- if (map[u][v] > w)
- {
- map[u][v] = w;
- map[v][u] = w;
- }
- }
-
- }
-
- void Dijkstra(int u)
- {
- memset(vis, 0, sizeof(vis));
- for (int t = 1; t <= n; t++)
- {
- dis[t] = map[u][t];
- }
- vis[u] = 1;
- for (int t = 1; t < n; t++)
- {
- int minn = Inf, temp;
- for (int i = 1; i <= n; i++)
- {
- if (!vis[i] && dis[i] < minn)
- {
- minn = dis[i];
- temp = i;
- }
- }
- vis[temp] = 1;
- for (int i = 1; i <= n; i++)
- {
- if (map[temp][i] + dis[temp] < dis[i])
- {
- dis[i] = map[temp][i] + dis[temp];
- }
- }
- }
-
- }
-
- int main()
- {
- /*
- input;
- 5 4
- 1 2 3
- 2 3 4
- 3 4 1
- 4 1 8
- 2 4 2*/
- scanf_s("%d%d", &m, &n);//5,4
- Init();
- Getmap();
- Dijkstra(n);//4
- printf("%d\n", dis[1]);
-
-
- return 0;
- }
参考文献:[1]https://www.roboticsproceedings.org/rss04/p28.pdf
- #include <stdio.h>
- #include <vector>
- using namespace std;
- #define ROWS 10
- #define COLS 10
-
- #define ZXDJ 10
- #define XXDJ 14
-
- enum direct { p_up, p_down, p_left, p_right, p_lup, p_ldown, p_rup, p_rdown };
-
- struct MyPoint {
- int row; //y
- int col; //x
- int f, g, h; //用来量化评估的
-
- void getF() { f = g + h; }
- };
-
- //树节点
- struct treeNode {
- MyPoint pos;
- treeNode* pParent;
- vector<treeNode*> child;
- };
-
- treeNode* createNode(MyPoint pos) {
- treeNode* pNew = new treeNode;
- //memset(pNew, 0, sizeof treeNode);//清空
- *pNew = { 0 };
- pNew->pos.row = pos.row;
- pNew->pos.col = pos.col;
- return pNew;
- }
-
- int getH(MyPoint pos, MyPoint endPos);
-
- int main() {
- //描述地图
- int map[ROWS][COLS] = {
- { 0, 0, 0, 0, 1, 0, 0, 0, 0, 0 },
- { 0, 0, 1, 1, 1, 0, 0, 0, 0, 0 },
- { 0, 1, 0, 1, 1, 0, 0, 0, 0, 0 },
- { 0, 1, 1, 0, 1, 0, 0, 0, 0, 0 },
- { 0, 0, 1, 1, 1, 0, 0, 0, 0, 0 },
- { 0, 0, 0, 0, 1, 0, 0, 0, 0, 0 },
- { 0, 0, 0, 0, 1, 0, 0, 0, 0, 0 },
- { 0, 0, 0, 0, 1, 0, 0, 0, 0, 0 },
- { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
- { 0, 0, 0, 0, 1, 0, 0, 0, 0, 0 }
- };
- bool pathMap[ROWS][COLS] = { 0 };//全部都是false 没有走过
- //起点和终点
- MyPoint begPos = { 1, 1 };
- MyPoint endPos = { 6, 7 };
-
- pathMap[begPos.row][begPos.col] = true;//起点标记走过
- treeNode* pRoot = createNode(begPos);//起点成为树根
-
- //准备一个数组用来存储并获取f最小的点
- vector<treeNode*> buff;
-
- vector<treeNode*>::iterator it;
- vector<treeNode*>::iterator itMin;
-
- treeNode* pCurrent = pRoot;//当前点
- bool isFindEnd = false;
-
-
-
- //寻路
- while (1) {
- //当前点发散出8个点
- for (int i = 0; i < 8; i++) {
- treeNode* pTemp = createNode(pCurrent->pos);
- switch (i)
- {
- case p_up:
- pTemp->pos.row--;
- pTemp->pos.g += ZXDJ;
- break;
- case p_down:
- pTemp->pos.row++;
- pTemp->pos.g += ZXDJ;
- break;
- case p_left:
- pTemp->pos.col--;
- pTemp->pos.g += ZXDJ;
- break;
- case p_right:
- pTemp->pos.col++;
- pTemp->pos.g += ZXDJ;
- break;
- case p_lup:
- pTemp->pos.row--;
- pTemp->pos.col--;
- pTemp->pos.g += XXDJ;
- break;
- case p_ldown:
- pTemp->pos.row++;
- pTemp->pos.col--;
- pTemp->pos.g += XXDJ;
- break;
- case p_rup:
- pTemp->pos.row--;
- pTemp->pos.col++;
- pTemp->pos.g += XXDJ;
- break;
- case p_rdown:
- pTemp->pos.row++;
- pTemp->pos.col++;
- pTemp->pos.g += XXDJ;
- break;
- }//end of switch
- //能走的才考虑 已经走过的应该不考虑
- if (pathMap[pTemp->pos.row][pTemp->pos.col] == false &&
- map[pTemp->pos.row][pTemp->pos.col] == 0 &&
- pTemp->pos.row >= 0 && pTemp->pos.row < ROWS &&
- pTemp->pos.col >= 0 && pTemp->pos.col < COLS) {
- //计算h值
- pTemp->pos.h = getH(pTemp->pos, endPos);
- //计算f值
- pTemp->pos.getF();
- //入树
- pCurrent->child.push_back(pTemp);
- pTemp->pParent = pCurrent;
- //数组存储
- buff.push_back(pTemp);
- }
- else {//不能走
- //delete pTemp;//释放pTemp
- }
- }//end of for
- //找出buff中 f最小的节点
- itMin = buff.begin();//假设第一个的f值最小
- //从第一个找到最后一个
- for (it = buff.begin(); it != buff.end(); it++) {
- itMin = (((*itMin)->pos.f < (*it)->pos.f) ? itMin : it);
- }
- //pCurrent指向它
- pCurrent = *itMin;
- pathMap[pCurrent->pos.row][pCurrent->pos.col] = true;//标记走过
- printf("current(%d,%d)\n", pCurrent->pos.row, pCurrent->pos.col);
- //buff中删掉它
- buff.erase(itMin);
- //是否到达终点
- if (pCurrent->pos.row == endPos.row &&
- pCurrent->pos.col == endPos.col) {
- isFindEnd = true;
- break;
- }
- //是否buff空了
- if (buff.size() == 0) break;
- }//end of while
-
- if (isFindEnd) {
- printf("找到终点了!\n");
- while (pCurrent) {
- printf("(%d,%d)", pCurrent->pos.row, pCurrent->pos.col);
- pCurrent = pCurrent->pParent;
- }
- printf("\n");
- }
-
- while (1);
- return 0;
- }
-
- int getH(MyPoint pos, MyPoint endPos) {
- int x = ((pos.col > endPos.col) ? (pos.col - endPos.col) : (endPos.col - pos.col));
- int y = ((pos.row > endPos.row) ? (pos.row - endPos.row) : (endPos.row - pos.row));
-
- return (x + y) * ZXDJ;
- }
参考文献:https://ieeexplore.ieee.org/document/351061
- #pragma once
- #include<vector>
- #include<queue>
- #include<memory>
- #include<algorithm>
- #include<iostream>
- namespace DStar {
- enum State
- {
- New,
- Open,
- Closed
- };
- struct DNode {
- explicit DNode(int X, int Y, DNode* Next = nullptr) : x(X), y(Y), next(Next) {}
- DNode() = default;
- void setObstacle()
- {
- is_obstacle = true;
- }
- int x = 0;
- int y = 0;
- int H = 0; // distance to target
- int K = 0; //所有时刻最小的H!
- State state = New;
- DNode* next = nullptr;
- bool is_obstacle = false;
- };
- struct MyCompare
- {
- bool operator()(DNode* lhs, DNode* rhs) const {
- return lhs->K > rhs->K;
- }
- };
- class DStar {
- public:
- DStar(const std::vector<std::vector<int>> map) : Map(map), shortestPaths(map.size(), std::vector<DNode*>(map.front().size(), nullptr)) {}
- void find_first_path(const std::pair<int, int>& start, const std::pair<int, int>& target, const std::vector<std::pair<int, int>>& obstacles);
- ~DStar()
- {
- for (int i = 0; i < shortestPaths.size(); ++i)
- {
- for (int j = 0; j < shortestPaths.front().size(); ++j)
- {
- if (shortestPaths[i][j])
- delete shortestPaths[i][j];
- }
- }
- }
- private:
- int cost(DNode* lhs, DNode* rhs) const;
- void insert(DNode* node, int Cost);
- //核心函数
- int process_state();
- int modify(DNode* node);
- void setObstacles(const std::vector<std::pair<int, int>>& obstacles);
-
- private:
- const static int _cost_low = 10;
- const static int _cost_high = 14;
- const static int _cost_max = 65536;
- std::priority_queue<DNode*, std::vector<DNode*>, MyCompare> openlist;
- std::vector<std::vector<int>> Map;
- std::vector<std::vector<DNode*>> shortestPaths; //保存每个节点到终点的最短路径信息
- };
- int DStar::cost(DNode* lhs, DNode* rhs) const
- {
- if (lhs->is_obstacle || rhs->is_obstacle)
- return _cost_max;
- if (lhs->x != rhs->x && lhs->y != rhs->y)
- return _cost_high;
- else
- return _cost_low;
- }
- void DStar::insert(DNode* node, int new_H)
- {
- new_H = (new_H >= _cost_max) ? _cost_max : new_H;
- if (node->state == New)
- {
- node->H = new_H;
- node->K = new_H;
- node->state = Open;
- shortestPaths[node->x][node->y] = node;
- openlist.push(node);
- }
- else if (node->state == Open) //节点已经在openlist中 那么只需要改变对应openlist位置的节点的H和K即可
- {
-
- node->H = new_H;
- node->K = std::min(node->K, new_H);
- }
- else
- {
- node->K = std::min(node->H, new_H);
- node->H = new_H;
- node->state = Open;
- openlist.push(node);
- }
- }
- int DStar::process_state()
- {
- DNode* cur_min = openlist.top();
- if (!cur_min)
- return -1;
- openlist.pop();
- cur_min->state = Closed;
- int K_old = cur_min->K;
- if (K_old < cur_min->H)
- {
- for (int i = cur_min->x - 1; i <= cur_min->x + 1; ++i)
- {
- for (int j = cur_min->y - 1; j <= cur_min->y + 1; ++j)
- {
- if (i >= 0 && j >= 0 && i < Map.size() && j < Map.front().size() && shortestPaths[i][j])
- {
- if (i == cur_min->x && j == cur_min->y)
- continue;
- if (shortestPaths[i][j]->H <= K_old && cur_min->H > shortestPaths[i][j]->H + cost(cur_min, shortestPaths[i][j]))
- {
- cur_min->H = shortestPaths[i][j]->H + cost(cur_min, shortestPaths[i][j]);
- cur_min->next = shortestPaths[i][j];
- }
- }
- }
- }
- }
- if (K_old == cur_min->H)
- {
- for (int i = cur_min->x - 1; i <= cur_min->x + 1; ++i)
- {
- for (int j = cur_min->y - 1; j <= cur_min->y + 1; ++j)
- {
- if (i >= 0 && j >= 0 && i < Map.size() && j < Map.front().size())
- {
- if (i == cur_min->x && j == cur_min->y)
- continue;
- if (!shortestPaths[i][j] && !Map[i][j]) //表示当前节点为New
- {
- DNode* neighbor = new DNode(i, j, cur_min);
- insert(neighbor, cur_min->H + cost(neighbor, cur_min));
- }
- else if (shortestPaths[i][j] && !shortestPaths[i][j]->is_obstacle)
- {
- if ((shortestPaths[i][j]->next == cur_min && shortestPaths[i][j]->H != cur_min->H + cost(shortestPaths[i][j], cur_min))
- || (shortestPaths[i][j]->next != cur_min && shortestPaths[i][j]->H > cur_min->H + cost(shortestPaths[i][j], cur_min)))
- {
- insert(shortestPaths[i][j], cur_min->H + cost(shortestPaths[i][j], cur_min));
- shortestPaths[i][j]->next = cur_min;
- }
- }
- }
- }
- }
- }
- else
- {
- //传递raise状态
- for (int i = cur_min->x - 1; i <= cur_min->x + 1; ++i)
- {
- for (int j = cur_min->y - 1; j <= cur_min->y + 1; ++j)
- {
- if (i == cur_min->x && j == cur_min->y)
- continue;
- if (i >= 0 && j >= 0 && i < Map.size() && j < Map.front().size())
- {
- if (!shortestPaths[i][j] && !Map[i][j]) //表示当前节点为New
- {
- DNode* neighbor = new DNode(i, j, cur_min);
- insert(neighbor, cur_min->H + cost(neighbor, cur_min));
- }
- else if (shortestPaths[i][j] && !shortestPaths[i][j]->is_obstacle)
- {
- if (shortestPaths[i][j]->next == cur_min && shortestPaths[i][j]->H != cur_min->H + cost(cur_min, shortestPaths[i][j]))
- {
- insert(shortestPaths[i][j], cur_min->H + cost(cur_min, shortestPaths[i][j]));
- }
- else
- {
- if (shortestPaths[i][j]->next != cur_min)
- {
- int temp = (shortestPaths[i][j]->H + cost(shortestPaths[i][j], cur_min) >= _cost_max) ? _cost_max : shortestPaths[i][j]->H + cost(shortestPaths[i][j], cur_min);
- if (cur_min->H < temp)
- insert(cur_min, cur_min->H);
- else if (shortestPaths[i][j]->next != cur_min && cur_min->H > shortestPaths[i][j]->H + cost(shortestPaths[i][j], cur_min)
- && shortestPaths[i][j]->state == Closed && shortestPaths[i][j]->K > K_old)
- {
- insert(shortestPaths[i][j], shortestPaths[i][j]->H);
- }
- }
- }
- }
- }
- }
- }
- }
- return openlist.top()->K;
- }
- void DStar::setObstacles(const std::vector<std::pair<int, int>>& obstacles)
- {
- if (obstacles.empty())
- return;
- for (const auto& rhs : obstacles)
- {
- if (shortestPaths[rhs.first][rhs.second])
- {
- shortestPaths[rhs.first][rhs.second]->is_obstacle = true;
- shortestPaths[rhs.first][rhs.second]->H = _cost_max;
- }
- Map[rhs.first][rhs.second] = '#';
- }
- }
- int DStar::modify(DNode* node)
- {
- DNode* next = node->next;
- openlist.push(next);
- int k_old;
- do {
- k_old = process_state();
- if (k_old == -1)
- break;
- } while (node->H == _cost_max || k_old < node->H);
- return k_old;
- }
- void DStar::find_first_path(const std::pair<int, int>& start, const std::pair<int, int>& target,
- const std::vector<std::pair<int, int>>& obstacles)
- {
- DNode* end = new DNode(target.first, target.second);
- shortestPaths[target.first][target.second] = end;
- openlist.push(end);
- while (true)
- {
- process_state();
- if (shortestPaths[start.first][start.second] && shortestPaths[start.first][start.second]->state == Closed)
- break;
- }
- setObstacles(obstacles);
- DNode* begin = shortestPaths[start.first][start.second];
- int i;
- while (begin)
- {
- Map[begin->x][begin->y] = '*';
- if (begin->next && begin->next->is_obstacle)
- {
- i = modify(begin);
- if (i == -1)
- {
- break;
- }
- }
- begin = begin->next;
- }
- if (i == -1)
- {
- std::cout << "No New Path To Target" << std::endl;
- return;
- }
- else
- {
- for (const auto& i : Map)
- {
- for (const auto& j : i)
- {
- if (j > 1)
- std::cout << char(j) << " ";
- else
- std::cout << j << " ";
- }
- std::cout << std::endl;
- }
- }
- }
- }
- #include <time.h>
- #include"DStar.h"
- int main()
- {
-
- std::vector<std::vector<int>> map2(25, std::vector<int>(25));
-
- for (int j = 3; j < 8; ++j)
- map2[6][j] = 1;
- for (int j = 4; j < 7; ++j)
- map2[7][j] = 1;
-
- clock_t start = clock();
- DStar::DStar d(map2);
- d.find_first_path({ 3, 2 }, { 23, 16 }, { {12, 4}, {12, 5}, {12, 6}, {12, 7}, {12, 8}, {12, 9}, {12, 10}, {12, 11}, {11, 7}, {13, 3}, {10, 6}, {14, 5}, {6, 2} });
- clock_t ends = clock();
- std::cout << "Running Time : " << (double)(ends - start) / CLOCKS_PER_SEC * 1000 << "ms" << std::endl;
- return 0;
- }
原文链接:基于C++的D*算法详解_dstar算法-CSDN博客
参考文献:https://www.ri.cmu.edu/pub_files/pub4/ferguson_david_2006_3/ferguson_david_2006_3.pdf
原文链接:Field D*路径规划算法_field d*-CSDN博客
参考文献:http://idm-lab.org/bib/abstracts/papers/aaai07a.pdf
扩展:Lazy Theta*
参考文献:https://www.sciencedirect.com/science/article/pii/S000437020800060X
参考文献:https://ieeexplore.ieee.org/document/4621302
参考文献:http://robots.stanford.edu/papers/junior08.pdf
参考文献:https://www.cs.cmu.edu/~alonzo/pubs/papers/TrajGenSubmitFinalCompressed.pdf
参考文献:Randomized kinodynamic planning | IEEE Conference Publication | IEEE Xplore
参考文献:https://www.ri.cmu.edu/pub_files/2012/5/ICRA12_xuwd_Final.pdf
参考文献: Pythagorean—Hodograph Curves
需要构建优化模型,设置目标函数,并考虑各种约束,比如运动学、动力学、障碍物、舒适性、安全性等等。
最常用的是基于插值的曲线路径生成,其次是基于图搜索的路径规划,其中最长用的是lattice planner。
从控制的角度来看,必须考虑多种约束,从车辆运动学限制到乘客舒适度。最近的发展旨在在规划阶段考虑这些限制因素,从而实现平滑和可实现的轨迹,减少控制阶段的限制。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。