基于海图栅格化的路径规划——Dijkstra算法

在海图栅格化的基础上跑下路径规划算法

Dijkstra算法源代码启发于运动规划入门 | 1. 白话Dijkstra,从原理到Matlab实现 - 古月居 (guyuehome.com)

初始化:导入的地图是之前自制的栅格地图,设置起点、目标点、读取地图中障碍物位置

clear;
clc;

%% 导入数据、初始化参数

% 导入数据,该数据集中0显示是黑色,1显示是白色
map_struct = load('map30_60.mat'); % 地图是之前栅格化后,保存为一个矩阵.mat
map_names = fieldnames(map_struct);
map_data = getfield(map_struct, map_names{1}); % 读取load的数据并重命名为map_data
% 绘制颜色图
cmap = [1 1 1; ...              % 1 - white - clear cell 
        0 0 0; ...              % 2 - black - obstacle 
               1 0 0; ...       % 3 - red - visited 
               0 0 1; ...       % 4 - blue - on list 
               0 1 0; ...       % 5 - green - start 
               1 1 0;           % 6 - yellow - destination 
               0 1 1];          % 7

map_data(map_data==0) = 2; % 为0的点形成障碍物; map_data==1的点本身就是白色,不需要重新设置
% 起点、终点设置
map_data(1, 1) = 5;                    % 起点 
map_data(20, 50) = 7;                  % 终点
image(1.5, 1.5, map_data);
colormap(cmap);
axis image; 
% nrows为行、ncols为列 
nrows = 30;  
ncols = 60;
% 起点、终点索引设置
start_node = sub2ind(size(map_data), 1, 1); % 起点坐标
dest_node = sub2ind(size(map_data), 20, 50); % 终点坐标
% 初始化cost、起点设置为0
distanceFromStart = Inf(nrows,ncols); 
distanceFromStart(start_node) = 0; 
% 初始化父节点矩阵为0 
parent = zeros(nrows,ncols); 

主循环:寻路并绘图,Dijkstra的一个特点是把所有合法的相邻节点都遍历,就像石头扔进水里溅起涟漪,一圈圈全遍历直到找到目标点。

想深入了解Dijkstra算法原理的可以去本文提到的链接去学习

while true 
 % 绘制当前图窗 
 map_data(start_node) = 5; 
 map_data(dest_node) = 6; 
 image(1.5, 1.5, map_data);
 grid on; 
 axis image; 
 drawnow; 

 [min_dist, current] = min(distanceFromStart(:)); % 找到未完全遍历节点中cost最小的节点
  if ((current == dest_node) || isinf(min_dist))
       break; 
  end

 map_data(current) = 3;
 distanceFromStart(current) = Inf;
 % 寻找四个相邻节点,判断临近节点是否合法,更新合法节点的cost和partent
 [i, j] = ind2sub(size(distanceFromStart), current); 
neighbor = [i-1,j;... 
            i+1,j;... 
            i,j+1;... 
            i,j-1] ;  % 当前节点的临近四个节点 
outRangetest = (neighbor(:,1)<1) + (neighbor(:,1)>nrows) +...
                   (neighbor(:,2)<1) + (neighbor(:,2)>ncols ) ;
locate = find(outRangetest>0);  % 返回大于0(不合法临节点)的索引
neighbor(locate,:)=[] ;
neighborIndex = sub2ind(size(map_data),neighbor(:,1),neighbor(:,2)) ;
for i=1:length(neighborIndex)  % 遍历合法节点的索引
    if (map_data(neighborIndex(i))~=2) && (map_data(neighborIndex(i))~=3 && map_data(neighborIndex(i))~= 5) 
        map_data(neighborIndex(i)) = 4;
        if distanceFromStart(neighborIndex(i))> min_dist + 1      
            distanceFromStart(neighborIndex(i)) = min_dist + 1;  % 相邻节点的cost为min_dist+1
            parent(neighborIndex(i)) = current;
        end 
    end 
end 
end
% 判断是否找到终点,找到了就提取路线
if (isinf(distanceFromStart(dest_node))) 
    route = [];
else 
    % 提取路线坐标
    route = dest_node; 
    while (parent(route(1)) ~= 0)  % 根据父节点顺藤摸瓜
        route = [parent(route(1)), route]; 
    end 
    % 动态显示出路线     
    for k = 2:length(route) - 1
        map_data(route(k)) = 7; 
        pause(0.1); 
        image(1.5, 1.5, map_data); 
        grid on; 
        axis image; 
    end 
end

附上结果图:

祝各位生活愉快

<think>好的,我现在需要帮助用户解决基于栅格法的船舶路径规划算法的问题。首先,我需要理解用户的需求。用户提到想要了解或实现基于栅格法的船舶路径规划算法,具体涉及栅格法、算法实现等方面。 首先,我应该回顾栅格法在路径规划中的基本概念。栅格法将环境划分为网格,每个网格代表一个可通行或障碍区域。对于船舶来说,可能需要考虑水流、水深等环境因素,这些可以集成到栅格地图中。接下来,我需要考虑如何将传统的栅格路径规划算法(如A*、Dijkstra)应用到船舶环境中,可能需要调整成本函数或考虑船舶的运动学约束。 然后,用户提到的引用中有提到双向蚁群算法、雾凇算法、Q-Learning和Dijkstra算法。这些方法各有优缺点,比如蚁群算法适合解决复杂路径问题,但可能需要调整参数;Dijkstra算法是确定性的,适合最短路径,但计算量大。船舶路径规划可能需要考虑动态环境或实时性,所以可能需要结合这些算法的优势。 接下来,我应该整理实现步骤。首先建立栅格地图,考虑船舶的特定环境因素。然后选择或改进路径搜索算法,可能需要将船舶的转弯半径、速度等因素纳入考虑。例如,A*算法的启发函数可以加入水深或水流的影响。此外,船舶的尺寸较大,可能需要处理栅格的分辨率,确保路径的安全性。 在具体实现方面,可能需要使用Matlab或Python。用户提供的引用中有Matlab代码的例子,但用户的问题没有明确指定语言,所以需要询问或建议两种语言的实现方式。同时,需要提到如何将环境数据转换为栅格地图,比如处理电子海图数据,将其栅格。 另外,船舶路径规划可能涉及三维栅格,比如考虑水深,但通常栅格法是二维的。可能需要分层处理,或者将水深作为栅格的属性之一。还需要考虑动态障碍物,比如其他船只,这可能需要在算法中加入实时避障机制。 用户可能还关心算法的评估指标,比如路径长度、计算时间、安全性等。需要讨论如何在这些指标之间权衡,例如使用多目标优方法。 最后,生成相关问题时要覆盖算法选择、环境建模、动态障碍物处理、性能优等,帮助用户进一步深入学习。 现在,我需要确保回答结构清晰,分步骤说明,并结合引用中的方法,比如提到双向蚁群算法和雾凇算法的优点,同时引用Dijkstra和Q-Learning的应用。需要指出不同算法在船舶场景中的适用性,并给出实现建议,比如使用Matlab进行仿真。</think>### 基于栅格法的船舶路径规划算法实现指南 #### 一、栅格法环境建模 1. **栅格地图构建** 将船舶航行区域划分为$m \times n$的栅格,每个栅格包含属性: - 障碍物标识(0可航行,1障碍) - 水深值$d_{ij}$(需满足船舶吃水深度$D$约束$d_{ij} \geq D$) - 水流速度矢量$\vec{v}_{ij}$ $$ \text{栅格成本} = \alpha \cdot d_{ij}^{-1} + \beta \cdot \|\vec{v}_{ij}\| $$ 其中$\alpha,\beta$为权重系数[^1] 2. **特殊约束处理** - 船舶最小转弯半径$R_{min}$对应栅格分辨率$\Delta x$需满足: $$ R_{min} \geq 2\Delta x $$ - 惯性约束通过扩展障碍物栅格实现[^4] #### 二、算法选择与改进 1. **改进A*算法** 启发函数增加水流影响因子: $$ h(n) = \|p_n - p_{goal}\| + \gamma \cdot \vec{v}_{ij} \cdot \vec{d}_{n\_goal} $$ $\gamma$为水流影响系数,$\vec{d}_{n\_goal}$为当前位置到目标的方向向量[^2] 2. **双向蚁群算法** 双向搜索策略显著提升效率: ```matlab % 双向信息素更新规则 pheromone = (1 - rho) * pheromone + ... delta_pheromone_forward + ... delta_pheromone_backward; [^1] ``` #### 三、实现步骤(Matlab示例) 1. **环境初始** ```matlab % 创建20x30栅格地图 map = robotics.BinaryGrid(20,30,1); % 导入水深数据 depth_map = load('bathymetry.mat'); % 设置船舶约束 ship_draft = 5; % 吃水深度5米 ``` 2. **路径搜索核心逻辑** ```matlab function path = ship_astar(start, goal) open_list = PriorityQueue(); open_list.insert(start, 0); while ~open_list.isempty() current = open_list.pop(); if current == goal return reconstruct_path(came_from, current); end for neighbor = get_neighbors(current) new_cost = cost_so_far[current] + movement_cost(current, neighbor); if new_cost < cost_so_far[neighbor] cost_so_far[neighbor] = new_cost; priority = new_cost + heuristic(neighbor, goal); open_list.insert(neighbor, priority); came_from[neighbor] = current; end end end end ``` 3. **可视输出** ```matlab show(map) hold on plot(path(:,1), path(:,2), 'r-', 'LineWidth',2) quiver(vx_map, vy_map) % 显示水流场 ``` #### 四、关键问题解决方案 1. **动态障碍物处理** 采用滚动窗口法实时更新局部栅格地图,结合速度障碍法(VO)进行在线避碰: $$ VO = \{ v | \exists t \in [0,\tau], (p_{ship} + vt) \in \Omega_{obs} \} $$ 其中$\tau$为预测时间窗口[^3] 2. **多目标优** 建立帕累托前沿面: $$ \min \left[ \sum_{k=1}^n C_k, \sum_{k=1}^n T_k, \sum_{k=1}^n R_k \right] $$ $C_k$为航行成本,$T_k$为时间成本,$R_k$为风险成本[^2]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值