| | |
| | | package com.zy.asrs.wcs.core.utils; |
| | | |
| | | import com.alibaba.fastjson.JSON; |
| | | import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; |
| | | import com.zy.asrs.framework.common.SpringUtils; |
| | | import com.zy.asrs.framework.exception.CoolException; |
| | | import com.zy.asrs.wcs.core.model.NavigateNode; |
| | | import com.zy.asrs.wcs.core.model.PythonResult; |
| | | import com.zy.asrs.wcs.core.model.enums.MapNodeType; |
| | | import com.zy.asrs.wcs.system.entity.Dict; |
| | | import com.zy.asrs.wcs.system.service.DictService; |
| | | |
| | | import java.io.BufferedReader; |
| | | import java.io.IOException; |
| | | import java.io.InputStreamReader; |
| | | import java.util.ArrayList; |
| | | import java.util.List; |
| | | import java.util.PriorityQueue; |
| | |
| | | //Exist表用来存放已经出现过的结点。 |
| | | public ArrayList<NavigateNode> Exist = new ArrayList<NavigateNode>(); |
| | | |
| | | public NavigateNode astarSearch(NavigateNode start, NavigateNode end) { |
| | | //把第一个开始的结点加入到Open表中 |
| | | this.Open.add(start); |
| | | //把出现过的结点加入到Exist表中 |
| | | this.Exist.add(start); |
| | | //主循环 |
| | | while (Open.size() > 0) { |
| | | //取优先队列顶部元素并且把这个元素从Open表中删除 |
| | | NavigateNode current_node = Open.poll(); |
| | | //将这个结点加入到Close表中 |
| | | Close.add(current_node); |
| | | //对当前结点进行扩展,得到一个四周结点的数组 |
| | | ArrayList<NavigateNode> neighbour_node = extend_current_node(current_node); |
| | | //对这个结点遍历,看是否有目标结点出现 |
| | | for (NavigateNode node : neighbour_node) { |
| | | // G + H + E (对启发函数增加去拐点方案calcNodeExtraCost) |
| | | int gCost = calcNodeCost(current_node, node) * calcNodeExtraCost(current_node, node, end); |
| | | if (node.getX() == end.getX() && node.getY() == end.getY()) {//找到目标结点就返回 |
| | | //init_node操作把这个邻居结点的父节点设置为当前结点 |
| | | //并且计算出G, F, H等值 |
| | | node.setLastDistance(gCost); |
| | | node.init_node(current_node, end); |
| | | return node; |
| | | } |
| | | public String astarSearch(NavigateNode start, NavigateNode end, String pythonScriptPath) { |
| | | String maps = JSON.toJSONString(map); |
| | | String startStr = start.getX() + "-" + start.getY(); |
| | | String targetStr = end.getX() + "-" + end.getY(); |
| | | |
| | | //进行计算对G, F, H 等值 |
| | | node.setLastDistance(gCost); |
| | | node.init_node(current_node, end); |
| | | node.setH(calcNodeCost(node, end)); |
| | | node.setF(node.getG() + node.getH()); |
| | | |
| | | Open.add(node); |
| | | Exist.add(node); |
| | | //默认地图母轨方向x |
| | | String mapDirection = "x"; |
| | | DictService dictService = SpringUtils.getBean(DictService.class); |
| | | if (dictService != null) { |
| | | Dict dict = dictService.getOne(new LambdaQueryWrapper<Dict>() |
| | | .eq(Dict::getFlag, "direction_map") |
| | | .eq(Dict::getStatus, 1)); |
| | | if (dict != null) { |
| | | mapDirection = dict.getValue(); |
| | | } |
| | | } |
| | | //如果遍历完所有出现的结点都没有找到最终的结点,返回null |
| | | |
| | | ProcessBuilder processBuilder = new ProcessBuilder("python", pythonScriptPath, maps, startStr, targetStr, mapDirection); |
| | | processBuilder.redirectErrorStream(true); |
| | | |
| | | try { |
| | | Process process = processBuilder.start(); |
| | | |
| | | // 读取Python脚本的输出 |
| | | BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream())); |
| | | String line; |
| | | StringBuilder builder = new StringBuilder(); |
| | | while ((line = reader.readLine()) != null) { |
| | | builder.append(line); |
| | | } |
| | | |
| | | // 等待Python脚本执行完成 |
| | | int exitCode = process.waitFor(); |
| | | if (exitCode != 0) { |
| | | System.out.println("Python script exited with error code: " + exitCode); |
| | | return null; |
| | | } |
| | | reader.close(); |
| | | |
| | | if (builder.length() <= 0) { |
| | | return null; |
| | | } |
| | | |
| | | PythonResult result = JSON.parseObject(builder.toString(), PythonResult.class); |
| | | if (result.getCalcResult() != 200) { |
| | | return null; |
| | | } |
| | | |
| | | String path = result.getPath(); |
| | | return path; |
| | | } catch (IOException | InterruptedException e) { |
| | | e.printStackTrace(); |
| | | } |
| | | return null; |
| | | } |
| | | |
| | | // public NavigateNode astarSearch(NavigateNode start, NavigateNode end) { |
| | | // //把第一个开始的结点加入到Open表中 |
| | | // this.Open.add(start); |
| | | // //把出现过的结点加入到Exist表中 |
| | | // this.Exist.add(start); |
| | | // //主循环 |
| | | // while (Open.size() > 0) { |
| | | // //取优先队列顶部元素并且把这个元素从Open表中删除 |
| | | // NavigateNode current_node = Open.poll(); |
| | | // //将这个结点加入到Close表中 |
| | | // Close.add(current_node); |
| | | // //对当前结点进行扩展,得到一个四周结点的数组 |
| | | // ArrayList<NavigateNode> neighbour_node = extend_current_node(current_node); |
| | | // //对这个结点遍历,看是否有目标结点出现 |
| | | // for (NavigateNode node : neighbour_node) { |
| | | // // G + H + E (对启发函数增加去拐点方案calcNodeExtraCost) |
| | | // int gCost = calcNodeCost(current_node, node) * calcNodeExtraCost(current_node, node, end); |
| | | // if (node.getX() == end.getX() && node.getY() == end.getY()) {//找到目标结点就返回 |
| | | // //init_node操作把这个邻居结点的父节点设置为当前结点 |
| | | // //并且计算出G, F, H等值 |
| | | // node.setLastDistance(gCost); |
| | | // node.init_node(current_node, end); |
| | | // return node; |
| | | // } |
| | | // |
| | | // //进行计算对G, F, H 等值 |
| | | // node.setLastDistance(gCost); |
| | | // node.init_node(current_node, end); |
| | | // node.setH(calcNodeCost(node, end)); |
| | | // node.setF(node.getG() + node.getH()); |
| | | // |
| | | // Open.add(node); |
| | | // Exist.add(node); |
| | | // } |
| | | // } |
| | | // //如果遍历完所有出现的结点都没有找到最终的结点,返回null |
| | | // return null; |
| | | // } |
| | | |
| | | |
| | | public ArrayList<NavigateNode> extend_current_node(NavigateNode current_node) { |
| | | //默认地图母轨方向x |