A*算法实现路径规划后路径的显示错误总结

Astar astar;
	Point_stc start(maze.rows-20, maze.cols/2);
	Point_stc end(20, maze.cols/2);
	maze = maze/255;
	list<Point_stc *> path = astar.GetPath(start, end, false, maze);
    Point_stc *p = path.front();
    list<Point_stc *>::iterator testiterator;
    	int w = 0;
	//int m =0, n = 0;
    for(testiterator = path.begin(); testiterator != path.end(); testiterator++)
    {
	    m = (*testiterator)->x;
	    n = (*testiterator)->y;
	    cv::Point A = cv::Point(n,m);
	    cv::circle(maze, A, 0.1, cv::Scalar(255,255,255),0.1);
	    w++;
    }
	maze = maze*255;
//*/
    	cv::namedWindow("PATH");
	cv::imshow("PATH",maze);

	return result;
main.cpp


#include<iostream>
#include<vector>
#include "Astar.h"
#include <stdlib.h>
#include <string.h>
#include <fstream>
#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>

//using namespace cv;
using namespace std;
int main()
{
    int i = 0, j = 0;
	cv::Mat maze = cv::Mat(200, 200, CV_8UC1);
/*    
    int A[8][12] = {{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 },
                    { 1, 0, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1 },
                    { 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1 },
                    { 1, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1 },
                    { 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 1 },
                    { 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1 },
                    { 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 1 },
                    { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }
                   };
    int m, n;
    for(m = 0; m < maze.size(); m++)
    {
        for(n = 0; n < maze[m].size(); n++)
        {
            maze[m][n] = A[m][n];
            cout << maze[m][n] << " ";
        }
        cout << "\n";
    }
*/
    cv::Mat B = cv::Mat(200,200,CV_8UC1); 
    int map[200][200] = {0};
    ifstream infile;
    infile.open("data.txt");
    for(i = 0; i < 200; i ++)
    {
        for(j = 0; j < 200; j++)
        {
            infile >> map[i][j];
	    maze.at<uchar>(i, j) = map[i][j];//maze的取值为 0 or 1
	    //
	    (1 == map[i][j]) ? (map[i][j] = 255) : (map[i][j] = 0);
	    B.data[i*200+j]=map[i][j]; //B的取值为 0 or 255
            //cout << maze;
        }
	//cout << endl;
    }
    //cout << endl;
    infile.close();
    	cv::namedWindow("MAP");
	cv::imshow("MAP",B);
	cv::waitKey();
	//cv::Mat B1;
	//maze.copyTo(B);
//标出起始点与终点
	cv::Point kaishi = cv::Point(15,120);
	cv::Point jieshu = cv::Point(180,110);
	cv::circle(B, kaishi, 3, cv::Scalar(255,255,255),1);//白色
	cv::circle(B, jieshu, 3, cv::Scalar(255,255,255),1);
	cv::imshow("MAP",B);
	cv::waitKey();
	//cout << " start = " << map[120][15] << endl;
	//cout << " end = " << map[110][180] << endl;
	Astar astar;
//	astar.InitAstar(maze);

	//ÉèÖÃÆðÊŒºÍœáÊøµã
	Point_stc start(120, 15);
	Point_stc end(110, 180);
	map[15][120] = 2;
	map[180][110] = 2;
	//A*Ëã·šÕÒѰ·Ÿ¶
	list<Point_stc *> path = astar.GetPath(start, end, false, maze);
	//ŽòÓ¡
    Point_stc *p = path.front();
    list<Point_stc *>::iterator testiterator;
    	i = 0;
	int m =0, n = 0;
    for(testiterator = path.begin(); testiterator != path.end(); testiterator++)
    {
	    m = (*testiterator)->x;
	    n = (*testiterator)->y;
	    cv::Point A = cv::Point(n,m);
	    cv::circle(B, A, 0.1, cv::Scalar(255,255,255),0.1);
	    cout << "line :" << i <<"  "<<"("<< (*testiterator)->x << ", " << (*testiterator)->y << ")" << endl;
	    map[m][n] = 2;
        i++;
    }
    	cv::namedWindow("PATH");
	cv::imshow("PATH",B);
	cv::waitKey();
    for(i = 0; i < 200; i ++)
    {
        for(j = 0; j < 200; j++)
        {
            //cout << map[i][j];
        }
	//cout << endl;
    }
    //cout << endl;
	//system("pause");
    //getchar();
	return 0;
}

 

路径规划程序中函数list<Point_stc *> path = astar.GetPath(start, end, false, maze); 函数中的参数 maze 我改写后传的是 cv::Mat 类型, 传入maze的结果显示规划出来的路径是正确的

当用cv::Mat B传地图进来后结果是错误的 

原因总结:maze中的值是 0 or 1 ,而 B 中的值是 0 or 255,因此要路径规划的话最好把Mat中的值像最开始那样处理到 0 or 1 

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: A*算法是一种常用于寻找最短路径算法。下面给出一个万能通用的Matlab代码实现: ```matlab function shortestPath = A_star(startNode, goalNode, adjacencyMatrix, heuristic) numNodes = size(adjacencyMatrix, 1); % 获取节点数量 openSet = startNode; % 初始化开放集合 gScore = Inf(numNodes, 1); % 初始化gScore gScore(startNode) = 0; % 设置起始节点的gScore为0 fScore = Inf(numNodes, 1); % 初始化fScore fScore(startNode) = heuristic(startNode, goalNode); % 设置起始节点的fScore为启发式函数值 cameFrom = zeros(numNodes, 1); % 初始化cameFrom数组 while ~isempty(openSet) [~, current] = min(fScore(openSet)); % 从开放集合中选择fScore最小的节点作为当前节点 if current == goalNode shortestPath = reconstructPath(cameFrom, current); % 如果当前节点为目标节点,则重构路径并返回 return; end openSet(openSet == current) = []; % 从开放集合中移除当前节点 neighbors = find(adjacencyMatrix(current,:) > 0); % 获取当前节点的邻居节点 for i = 1:length(neighbors) neighbor = neighbors(i); tentativeGScore = gScore(current) + adjacencyMatrix(current, neighbor); % 从当前节点到邻居节点的距离 if tentativeGScore < gScore(neighbor) cameFrom(neighbor) = current; % 更新邻居节点的cameFrom gScore(neighbor) = tentativeGScore; % 更新邻居节点的gScore fScore(neighbor) = gScore(neighbor) + heuristic(neighbor, goalNode); % 更新邻居节点的fScore if ~ismember(neighbor, openSet) openSet(end+1) = neighbor; % 如果邻居节点不在开放集合中,则将其加入 end end end end error("No path found."); % 如果无法到达目标节点,则抛出错误 end function path = reconstructPath(cameFrom, current) path = current; while cameFrom(current) ~= 0 current = cameFrom(current); path = [current; path]; % 在路径之前添加上一个节点 end end ``` 上述代码实现了A*算法的最短路径搜索。其中,`startNode`表示起始节点的索引,`goalNode`表示目标节点的索引,`adjacencyMatrix`表示节点间的邻接矩阵,`heuristic`表示启发式函数。函数输出为一个表示最短路径的向量,即从起始节点到目标节点的节点索引序列。 这个代码适用于任何可以表示为图的最短路径问题,只需提供相应的起始节点、目标节点、邻接矩阵和启发式函数即可。 ### 回答2: A*算法是一种用于寻找最短路径的启发式搜索算法,在许多应用中被广泛使用。下面我将给出一个使用MATLAB实现的通用A*算法代码: ```matlab function path = AStar(start, goal, heuristic, cost) openSet = start; % 初始化openSet队列,包含起点 closedSet = []; % 初始化closedSet队列,不包含任何节点 gScore = inf(size(cost)); % 初始化gScore为无穷大 gScore(start) = 0; % 起点的gScore为0 fScore = inf(size(cost)); % 初始化fScore为无穷大 fScore(start) = heuristic(start, goal); % 起点的fScore为启发式函数的值 while ~isempty(openSet) [~, current] = min(fScore(openSet)); % 在openSet中找到fScore最小的节点作为当前节点 current = openSet(current); if current == goal % 当前节点为目标节点 path = reconstructPath(cameFrom, current); return; end openSet(openSet == current) = []; % 将当前节点从openSet中删除 closedSet = [closedSet, current]; % 添加当前节点到closedSet for neighbor = find(cost(current, :)) % 遍历当前节点的邻居节点 if ismember(neighbor, closedSet) % 跳过已经在closedSet中的节点 continue; end tentativeGScore = gScore(current) + cost(current, neighbor); % 计算从起点到邻居节点的临时gScore if ~ismember(neighbor, openSet) % 如果邻居节点不在openSet中 openSet = [openSet, neighbor]; % 将邻居节点添加到openSet elseif tentativeGScore >= gScore(neighbor) % 如果临时gScore不小于邻居节点的gScore continue; % 跳过当前循环 end cameFrom(neighbor) = current; % 更新邻居节点的cameFrom指针 gScore(neighbor) = tentativeGScore; % 更新邻居节点的gScore fScore(neighbor) = gScore(neighbor) + heuristic(neighbor, goal); % 更新邻居节点的fScore end end error("No path found!"); % 如果循环结束时仍未找到路径,抛出错误异常 end function path = reconstructPath(cameFrom, current) path(1) = current; % 从目标节点出发 while cameFrom(current) ~= 0 % 当前节点存在指向的前驱节点 current = cameFrom(current); % 回溯节点 path = [current, path]; % 添加到路径中 end end ``` 上述代码实现了一个基本的A*算法,其中使用了启发式函数(heuristic)和代价函数(cost)来评估节点的值。在代码中,我们首先初始化openSet队列,然后在每一次迭代中选择fScore最小的节点作为当前节点,然后通过遍历当前节点的邻居节点来更新节点的gScore和fScore。最后,如果找到了路径,我们通过回溯(reconstructPath)来生成最短路径。 这段代码可以根据具体的应用场景进行一定的修改和优化。 ### 回答3: A*算法是一种常用的图搜索算法,可以用于求解最短路径问题。下面是一个用MATLAB实现的通用的A*算法代码: ```matlab function path = Astar(graph, start, goal) % 初始化起点和终点节点 startNode = Node(start, [], 0, heuristic(start, goal)); goalNode = Node(goal, [], inf, inf); % 初始化开启列表和关闭列表 openList = PriorityList(); closeList = {}; % 将起点节点加入开启列表 openList.add(startNode); % 当开启列表不为空时,继续搜索 while ~openList.isEmpty() % 从开启列表中获取最佳节点 currentNode = openList.removeFirst(); % 将当前节点加入关闭列表 closeList{end+1} = currentNode; % 如果当前节点是目标节点,则找到最短路径 if currentNode == goalNode path = reconstructPath(currentNode); return; end % 获取当前节点的所有相邻节点 neighbors = getNeighbors(graph, currentNode); for i = 1:length(neighbors) neighbor = neighbors(i); % 跳过已经在关闭列表中的节点 if isNodeInList(neighbor, closeList) continue; end % 计算从起点到这个相邻节点的已知最短路径 tentative_gScore = currentNode.gScore + getDistance(currentNode, neighbor); % 判断这个相邻节点是否已经在开启列表 if ~openList.contains(neighbor) openList.add(neighbor); elseif tentative_gScore >= neighbor.gScore continue; end % 更新相邻节点的父节点和路径代价 neighbor.parent = currentNode; neighbor.gScore = tentative_gScore; neighbor.fScore = neighbor.gScore + heuristic(neighbor.position, goal); end end % 若无法找到最短路径,返回空 path = []; end function path = reconstructPath(lastNode) path = []; while ~isempty(lastNode) path = [lastNode.position path]; lastNode = lastNode.parent; end end function neighbors = getNeighbors(graph, node) neighbors = []; for i = 1:size(graph, 1) if graph(node.position, i) ~= 0 neighbors = [neighbors Node(i)]; end end end function distance = getDistance(nodeA, nodeB) distance = graph(nodeA.position, nodeB.position); end function h = heuristic(position, goal) h = abs(position - goal); end classdef Node < handle properties position parent gScore fScore end methods function obj = Node(position, parent, gScore, fScore) obj.position = position; obj.parent = parent; obj.gScore = gScore; obj.fScore = fScore; end function result = eq(obj, other) result = obj.position == other.position; end end end classdef PriorityList < handle properties list end methods function obj = PriorityList() obj.list = {}; end function add(obj, item) for i = 1:length(obj.list) if item.fScore < obj.list{i}.fScore obj.list = [obj.list(1:i-1) item obj.list(i:end)]; return; end end obj.list{end+1} = item; end function removeFirst(obj) if ~isempty(obj.list) obj.list = obj.list(2:end); end end function result = isEmpty(obj) result = isempty(obj.list); end function result = contains(obj, item) result = false; for i = 1:length(obj.list) if obj.list{i} == item result = true; return; end end end end end ``` 以上代码实现了A*算法的一个通用版本,可以通过修改图的邻接矩阵、起点和终点来解决不同的最短路径问题。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值