From 05ab248b187e867b8c07df547fca30b525dfe484 Mon Sep 17 00:00:00 2001 From: walker-sheng Date: Thu, 28 Jan 2021 16:36:07 +0800 Subject: [PATCH] =?UTF-8?q?=E8=BF=9B=E8=B7=AF=E8=B7=AF=E5=BE=84=E5=AF=B9?= =?UTF-8?q?=E8=B1=A1=E8=B0=83=E6=95=B4=20=E8=BF=9B=E8=B7=AF=E8=B7=AF?= =?UTF-8?q?=E5=BE=84=E6=9F=A5=E8=AF=A2=E6=96=B9=E6=B3=95=E9=87=8D=E5=86=99?= =?UTF-8?q?=20=E6=8C=89=E8=AE=A1=E5=88=92=E8=A1=8C=E8=BD=A6=E5=8A=A0?= =?UTF-8?q?=E8=BD=BD=E5=88=97=E8=BD=A6=E9=80=BB=E8=BE=91=E8=B0=83=E6=95=B4?= =?UTF-8?q?=20=E8=BF=9B=E8=B7=AF=E5=BB=B6=E7=BB=AD=E4=BF=9D=E6=8A=A4?= =?UTF-8?q?=E4=BE=A7=E9=98=B2=E9=80=BB=E8=BE=91=E9=97=AE=E9=A2=98=E4=BF=AE?= =?UTF-8?q?=E6=94=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../cbtc/ATS/service/AtsTrainLoadService.java | 23 +- .../cbtc/CI/service/RouteService.java | 58 +++-- .../cbtc/build/InterlockBuilder2.java | 3 - .../simulation/cbtc/build/RunPlanBuilder.java | 4 +- .../cbtc/data/CalculateService.java | 226 ++++++++++++------ .../rtss/simulation/cbtc/data/map/Route.java | 2 +- .../simulation/cbtc/data/map/RouteFls.java | 4 +- .../cbtc/data/support/RoutePath.java | 145 ++++++++++- 8 files changed, 329 insertions(+), 136 deletions(-) diff --git a/src/main/java/club/joylink/rtss/simulation/cbtc/ATS/service/AtsTrainLoadService.java b/src/main/java/club/joylink/rtss/simulation/cbtc/ATS/service/AtsTrainLoadService.java index 1153f056d..29e7dffd2 100644 --- a/src/main/java/club/joylink/rtss/simulation/cbtc/ATS/service/AtsTrainLoadService.java +++ b/src/main/java/club/joylink/rtss/simulation/cbtc/ATS/service/AtsTrainLoadService.java @@ -205,15 +205,10 @@ public class AtsTrainLoadService { RoutePath routePath = this.selectDefaultRoutePath(repository, stationPlan.getSection(), nextStationPlan.getSection()); right = routePath.isRight(); int t = current.toSecondOfDay() - stationPlan.getLeaveTime().toSecondOfDay(); - float s = routePath.getLenFromSection(stationPlan.getSection()); - //右:-最后区段+后右停车点 + 前区段-前右停车点 左:-左停车点+前左停车点 - s= right? - s-nextStationPlan.getSection().getLen()+nextStationPlan.getSection().getStopPointByDirection(right)+stationPlan.getSection().getLen()-stationPlan.getSection().getStopPointByDirection(right) - : - s-nextStationPlan.getSection().getStopPointByDirection(right)+stationPlan.getSection().getStopPointByDirection(right); + float totalLen = routePath.getLength(); int totalTime = nextStationPlan.getArriveTime().toSecondOfDay() - stationPlan.getLeaveTime().toSecondOfDay(); - float moveDistance = s / totalTime * t; // 移动的距离 - headPosition = routePath.getSectionPositionOfLen(moveDistance,stationPlan.getSection()); + float moveDistance = totalLen / totalTime * t; // 移动的距离 + headPosition = routePath.getSectionPositionOfLen(moveDistance); SectionPosition nextTargetPosition = new SectionPosition(nextStationPlan.getSection(), nextStationPlan.getSection().getStopPointByDirection(right)); if (headPosition.isAheadOf(nextTargetPosition, right)) { @@ -431,8 +426,6 @@ public class AtsTrainLoadService { trainInfo.updateEstimatedArriveInfo(endStationPlan.getSection(), endStationPlan.getArriveTime()); train.updateNextStationPlan(endStationPlan.getStation(), endStationPlan.getSection(), tripPlan.isPlanParking(endStationPlan)); break; - } else if (passedSectionStopPoint(headPosition, endStationPlan.getSection(), right)) { - continue; } else { RoutePath routePath = this.selectDefaultRoutePath(repository, startStationPlan.getSection(), endStationPlan.getSection()); if (routePath.containsSection(headPosition.getSection())) { @@ -461,16 +454,6 @@ public class AtsTrainLoadService { return false; } - - private boolean passedSectionStopPoint(SectionPosition headPosition, Section funSection, boolean right) { - float d = headPosition.getOffset() - funSection.getStopPointByDirection(right); - if (Objects.equals(headPosition.getSection(), funSection) - && d > SimulationConstants.PARK_POINT_MAX_OFFSET) { - return true; - } - return false; - } - /** * 处理碰撞逻辑 * @param simulation diff --git a/src/main/java/club/joylink/rtss/simulation/cbtc/CI/service/RouteService.java b/src/main/java/club/joylink/rtss/simulation/cbtc/CI/service/RouteService.java index 8b5a45526..68c998953 100644 --- a/src/main/java/club/joylink/rtss/simulation/cbtc/CI/service/RouteService.java +++ b/src/main/java/club/joylink/rtss/simulation/cbtc/CI/service/RouteService.java @@ -478,10 +478,12 @@ public class RouteService { return; } MapConfig config = simulation.getRepository().getConfig(); - if (simulation.getSystemTime().isAfter(overlap.getSettingStartTime().plusSeconds(10))) { - overlap.settingFailed(); - log.info(String.format("进路延续保护[%s]办理失败", overlap.debugStr())); - return; + if (!config.isRouteSettingNoFail()) { + if (simulation.getSystemTime().isAfter(overlap.getSettingStartTime().plusSeconds(10))) { + overlap.settingFailed(); + log.info(String.format("进路延续保护[%s]办理失败", overlap.debugStr())); + return; + } } boolean right = overlap.isRight(); SectionPath sectionPath = overlap.selectPath(); @@ -515,26 +517,22 @@ public class RouteService { } } List switchList = sectionPath.getSwitchList(); - if (!overlap.isRequisition()) { // 设备征用 - // 延续保护位置转动 - this.routeSwitchTurn(simulation, switchList); - List flsList = sectionPath.getFlsList(); - this.routeFlsControl(simulation, flsList); - if (config.isLockFirst()) { - for (SwitchElement switchElement : switchList) { - switchElement.getASwitch().overlapLock(); - } - if (!CollectionUtils.isEmpty(flsList)) { - for (RouteFls routeFls : flsList) { - routeFls.lock(); - } + List flsList = sectionPath.getFlsList(); + // 延续保护位置转动 + this.routeSwitchTurn(simulation, switchList); + this.routeFlsControl(simulation, flsList); + if (config.isLockFirst()) { + for (SwitchElement switchElement : switchList) { + switchElement.getASwitch().overlapLock(); + } + if (!CollectionUtils.isEmpty(flsList)) { + for (RouteFls routeFls : flsList) { + routeFls.lock(); } } - overlap.updateRequisition(true); - return; } // 道岔是否转换到位置 - boolean onPosition = this.checkRouteSwitchPosition(switchList); + boolean onPosition = this.checkRouteSwitchPosition(switchList) && this.isFlsSwitchOnPosition(flsList); if (!onPosition) return; // 未到位,返回 if (!overlap.getSection().isRouteLock()) { return; @@ -544,6 +542,26 @@ public class RouteService { log.debug(String.format("进路延续保护[%s]办理成功", overlap.debugStr())); } + private boolean isFlsSwitchOnPosition(List flsList) { + if (!CollectionUtils.isEmpty(flsList)) { + for (RouteFls routeFls : flsList) { + List level1List = routeFls.getLevel1List(); + for (RouteFls.FlsElement flsElement : level1List) { + SwitchElement pSwitch = flsElement.getPSwitch(); + if (pSwitch != null && !pSwitch.getASwitch().isOnPosition(pSwitch.isNormal())) { + return false; + } else { + SwitchElement fpae = flsElement.getFpae(); + if (fpae != null && !fpae.getASwitch().isOnPosition(fpae.isNormal())) { + return false; + } + } + } + } + } + return true; + } + private boolean checkRouteSwitchPosition(List switchList) { if (!CollectionUtils.isEmpty(switchList)) { for (SwitchElement switchElement : switchList) { diff --git a/src/main/java/club/joylink/rtss/simulation/cbtc/build/InterlockBuilder2.java b/src/main/java/club/joylink/rtss/simulation/cbtc/build/InterlockBuilder2.java index 5ded62d62..73d4a75cc 100644 --- a/src/main/java/club/joylink/rtss/simulation/cbtc/build/InterlockBuilder2.java +++ b/src/main/java/club/joylink/rtss/simulation/cbtc/build/InterlockBuilder2.java @@ -758,9 +758,6 @@ public class InterlockBuilder2 { errMsgList.add(String.format("站间运行等级[%s]无法找到路径", runLevel.debugStr(), startSection.debugStr(), endSection.debugStr())); } else { - for (RoutePath routePath : routePaths) { - routePath.calculateDistance(); - } routePathMap.put(routePaths.get(0).getKey(), routePaths); } } diff --git a/src/main/java/club/joylink/rtss/simulation/cbtc/build/RunPlanBuilder.java b/src/main/java/club/joylink/rtss/simulation/cbtc/build/RunPlanBuilder.java index 38be9048e..b0f81d508 100644 --- a/src/main/java/club/joylink/rtss/simulation/cbtc/build/RunPlanBuilder.java +++ b/src/main/java/club/joylink/rtss/simulation/cbtc/build/RunPlanBuilder.java @@ -269,7 +269,7 @@ public class RunPlanBuilder { StationPlan firstStationPlan = tripPlan.getFirstStationPlan(); if (!Objects.equals(startSection.getCode(), firstStationPlan.getSection().getCode()) && - !Objects.equals(startSection.getDeviceStation().getCode(), firstStationPlan.getStation().getCode())) { + !Objects.equals(startSection.getStation().getCode(), firstStationPlan.getStation().getCode())) { log.warn(String.format("计划车次[%s|%s|%s]起始区段[%s(%s)]错误:既不是第一个车站[%s(%s)]到发计划的停靠区段[%s(%s)],也不属于第一个到站计划车站", tripPlan.getServiceNumber(), tripPlan.getTripNumber(), tripPlan.getDestinationCode(), startSection.getName(), @@ -280,7 +280,7 @@ public class RunPlanBuilder { } StationPlan lastStationPlan = tripPlan.getLastStationPlan(); if (!Objects.equals(endSection.getCode(), lastStationPlan.getSection().getCode()) && - !Objects.equals(endSection.getDeviceStation().getCode(), lastStationPlan.getStation().getCode())) { + !Objects.equals(endSection.getStation().getCode(), lastStationPlan.getStation().getCode())) { log.warn(String.format("计划车次[%s|%s|%s]结束区段[%s(%s)]错误:既不是最后车站[%s(%s)]到发计划的停靠区段[%s(%s)],也不属于最后到站的计划车站", tripPlan.getServiceNumber(), tripPlan.getTripNumber(), tripPlan.getDestinationCode(), endSection.getName(), diff --git a/src/main/java/club/joylink/rtss/simulation/cbtc/data/CalculateService.java b/src/main/java/club/joylink/rtss/simulation/cbtc/data/CalculateService.java index b800e6701..f29a3efa8 100644 --- a/src/main/java/club/joylink/rtss/simulation/cbtc/data/CalculateService.java +++ b/src/main/java/club/joylink/rtss/simulation/cbtc/data/CalculateService.java @@ -85,7 +85,6 @@ public class CalculateService { * 计算从起点到终点距离(单方向) */ public static Float calculateDistance(SectionPosition startPosition, SectionPosition endPosition, boolean right) { -// long start = System.currentTimeMillis(); Section startSection = startPosition.getSection(); Section endSection = endPosition.getSection(); float distance = 0; @@ -119,8 +118,6 @@ public class CalculateService { distance += baseOffset - endPosition.getOffset(); } } -// long end = System.currentTimeMillis(); -// System.out.println(String.format("计算距离用时:%s", (end-start))); return distance; } @@ -640,99 +637,174 @@ public class CalculateService { public static List queryRoutePathsOnDirection(Section start, Section end, Boolean right) { List list = new ArrayList<>(); - Signal signal = null; -// if (start.isSwitchTrack()) { -// signal = start.querySwitchSectionRelatedSignalByDirection(right); -// } else { -// signal = start.getSignalOf(right); -// } - Section section = start; - int rc = 0; - while (signal == null && rc < 20) { - ++rc; - if (section == null) { - break; - } - signal = section.getSignalOf(right); - if (signal != null) { - break; - } - Section sectionOf = section.getSectionOf(!right); - if (sectionOf != null) { - section = sectionOf; - } else if (sectionOf == null && section.isSwitchTrack()) { - Switch relSwitch = section.getRelSwitch(); - if (relSwitch.isA(section)) { - section = relSwitch.getB(); - } else { - section = relSwitch.getA(); - } - } - } + List warnList = new ArrayList<>(); RoutePath routePath = new RoutePath(start, end, right); - getRoutePaths(signal, right, end, 1, routePath, list); + queryRoutePaths(0, start, routePath, list, warnList); + if (!CollectionUtils.isEmpty(list)) { + for (RoutePath path : list) { + path.calculateDistance(); + log.debug(path.debugStr2()); + } + } else { + log.warn(String.format("进路路径[%s]未找到:[%s]", + routePath.debugStr(), + String.join(",", warnList))); + } return list; } - private static void getRoutePaths(Signal signal, Boolean right, Section end, int iter, - RoutePath routePath, List list) { - if (Objects.isNull(signal)) { + private static void queryRoutePaths(int iter, Section section, RoutePath routePath, + List list, List warnList) { + if (section == null) { + warnList.add(String.format("进路路径[%s]未找到,找到的最后区段为[%s],下一区段为null", + routePath.debugStr(), routePath.getLastSection().debugStr())); return; } - if (iter > 20) { + if (iter > 10) { + warnList.add(String.format("进路路径[%s]未找到:迭代10次,最后区段为[%s]", + routePath.debugStr(), routePath.getLastSection().debugStr())); return; } + Section end = routePath.getEnd(); + boolean right = routePath.isRight(); + Signal signal = section.getSignalOf(right); + if (signal == null) { + // 区段没有信号机 + Section next = section.getSectionOf(right); + if (next != null) { + // 下一区段存在 + if (Objects.equals(next, end)) { + // 找到,结束 + list.add(routePath); + } else { + // 添加并进行迭代 + routePath.addSection(next); + queryRoutePaths(iter + 1, next, routePath, list, warnList); + } + } else if (section.isSwitchTrack()) { // 道岔区段 + Switch relSwitch = section.getRelSwitch(); + if (relSwitch.isA(section)) { + RoutePath path1 = routePath.cloneNew(); + path1.addSection(relSwitch.getB()); + queryRoutePaths(iter + 1, relSwitch.getB(), path1, list, warnList); + RoutePath path2 = routePath.cloneNew(); + path2.addSection(relSwitch.getC()); + queryRoutePaths(iter + 1, relSwitch.getC(), path2, list, warnList); + } else { + routePath.addSection(relSwitch.getA()); + queryRoutePaths(iter + 1, relSwitch.getA(), routePath, list, warnList); + } + } else { + warnList.add(String.format("区段[%s]的[%s]区段不存在", + section.debugStr(), right ? "右向" : "左向")); + } + return; + } + // 信号机存在 routePath.addSignal(signal); List routeList = signal.getRouteList(); if (!CollectionUtils.isEmpty(routeList)) { - // 根据信号机的进路查询 - Set signals = new HashSet<>(); - for (Route route : routeList) { - if (route.isGround() || route.isGuide()) { // 如果进路是分为ATP信号、地面信号、引导信号的,只处理ATP信号 - continue; + // 进路 + boolean find = false; + if (signal.isVirtual()) { // 虚拟信号机,应该只有一条进路 + BusinessExceptionAssertEnum.SYSTEM_EXCEPTION.assertTrue(routeList.size() == 1); + Route route = routeList.get(0); + routePath.addRoute(route); + List
sectionList = route.getSectionList(); + int i = sectionList.indexOf(end); + if (i >= 0) { + // 找到 + routePath.addSections(sectionList.subList(0, i)); + list.add(routePath); + } else { + routePath.addSections(sectionList); + queryRoutePaths(iter+1, route.getLastRouteSection(), routePath, list, warnList); } - if (route.isRouteSection(end)) { - for (Section section : route.getSectionList()) { - routePath.addSection(section); - if (Objects.equals(section, end)) { - break; + return; + } + Map> routeMap = new HashMap<>(); // 进路终端对应进路列表(ATP进路合并进正常进路终端) + routeList.sort(Comparator.comparing(Route::isAtp)); // 将ATP进路排在最后处理 + for (Route route : routeList) { + Section lastRouteSection = route.getLastRouteSection(); + List routes = routeMap.get(lastRouteSection); + if (routes == null) { + routes = new ArrayList<>(); + routeMap.put(lastRouteSection, routes); + } + routes.add(route); + if (route.isAtp()) { // 哈尔滨一ATP进路 + boolean handled = false; + Set
sections = routeMap.keySet(); + for (Section last : sections) { + List tempList = routeMap.get(last); + if (tempList.contains(lastRouteSection)) { + handled = true; + tempList.add(route); + List nextRouteList = route.getDestination().getRouteList(); + if (nextRouteList.size() == 1 && + Objects.equals(nextRouteList.get(0).getLastRouteSection(), last)) { + tempList.addAll(nextRouteList); + } else { + throw BusinessExceptionAssertEnum.SYSTEM_EXCEPTION.exception(); + } } } - list.add(routePath); - return; - } else { - signals.add(route.getDestination()); + if (handled) { + routeMap.remove(lastRouteSection); + } } } - if (!CollectionUtils.isEmpty(signals)) { - for (Signal endSignal : signals) { - RoutePath clone = routePath.cloneNew(); - for (Route route : routeList) { - if (Objects.equals(route.getDestination(), endSignal)) { - clone.addSections(route.getSectionList()); - break; - } + Set
keys = routeMap.keySet(); + List iterList = new ArrayList<>(); + for (Section key : keys) { + List routeList1 = routeMap.get(key); + List
sectionList = routeList1.get(0).getSectionList(); + int i = sectionList.indexOf(end); + if (i >= 0) { + // 找到 + routePath.addRoutes(routeList1); + if (!find) { + find = true; + routePath.addSections(sectionList.subList(0, i)); } - getRoutePaths(endSignal, right, end, iter + 1, clone, list); + } else { + // 不包含 + RoutePath clone = routePath.cloneNew(); + clone.addRoutes(routeList1); + clone.addSections(sectionList); + iterList.add(clone); + } + } + if (find) { + list.add(routePath); + return; + } else { + for (RoutePath clone : iterList) { + Section next = clone.getLastSection(); + queryRoutePaths(iter + 1, next, clone, list, warnList); } } } else { - // 循着自动信号后面的区段查询 + // 自动信号 AutoSignal autoSignal = signal.getAutoSignal(); - if (Objects.nonNull(autoSignal)) { - List
sectionList = autoSignal.getSectionList(); - for (Section section : sectionList) { - routePath.addSection(section); - if (Objects.equals(section, end)) { - list.add(routePath); - return; - } else { - Signal signalOf = section.getSignalOf(right); - if (Objects.nonNull(signalOf)) { - RoutePath clone = routePath.cloneNew(); - getRoutePaths(signalOf, right, end, iter + 1, clone, list); - break; - } + if (autoSignal == null) { + warnList.add(String.format("信号机[%s]既没有进路也不是自动信号", signal.debugStr())); + return; + } + List
sectionList = autoSignal.getSectionList(); + int i = sectionList.indexOf(end); + if (i >= 0) { + // 找到 + routePath.addSections(sectionList.subList(0, i)); + list.add(routePath); + return; + } else { + // 顺着区段找下一个有信号机的区段为止 + for (Section next : sectionList) { + routePath.addSection(next); + if (next.getSignalOf(right) != null) { + queryRoutePaths(iter + 1, next, routePath, list, warnList); + break; } } } @@ -742,8 +814,8 @@ public class CalculateService { /** * 查找从startSection到destination的途径区段路径 */ - public static Set> querySectionPaths2Destination(@NonNull Section startSection, @NonNull Section destination, - @NonNull Boolean right, @NonNull boolean stop) { + public static Set> querySectionPaths2Destination(Section startSection, Section destination, + Boolean right, boolean stop) { long start = System.currentTimeMillis(); //从startSection开始寻找第一个同向信号机(如果是折返轨,两边的信号机都算),并记录途径区段 List signals = new ArrayList<>(); diff --git a/src/main/java/club/joylink/rtss/simulation/cbtc/data/map/Route.java b/src/main/java/club/joylink/rtss/simulation/cbtc/data/map/Route.java index 6a019593b..bed268f0b 100644 --- a/src/main/java/club/joylink/rtss/simulation/cbtc/data/map/Route.java +++ b/src/main/java/club/joylink/rtss/simulation/cbtc/data/map/Route.java @@ -35,7 +35,7 @@ public class Route extends MapNamedElement { /** 是否折返进路 */ private boolean turnBack; - /** 是否引导进路 */ + /** 是否ATP进路 */ private boolean atp; /** 是否地面信号进路 */ diff --git a/src/main/java/club/joylink/rtss/simulation/cbtc/data/map/RouteFls.java b/src/main/java/club/joylink/rtss/simulation/cbtc/data/map/RouteFls.java index b171c460b..d8d1858e1 100644 --- a/src/main/java/club/joylink/rtss/simulation/cbtc/data/map/RouteFls.java +++ b/src/main/java/club/joylink/rtss/simulation/cbtc/data/map/RouteFls.java @@ -64,11 +64,11 @@ public class RouteFls { public void lock() { for (FlsElement flsElement : this.getLevel1List()) { SwitchElement pSwitch = flsElement.getPSwitch(); - if (pSwitch != null) { + if (pSwitch != null && !pSwitch.getASwitch().isSectionOccupied()) { pSwitch.getASwitch().fpLock(); } else { SwitchElement fpae = flsElement.getFpae(); - if (fpae != null) { + if (fpae != null && !fpae.getASwitch().isSectionOccupied()) { fpae.getASwitch().fpLock(); } } diff --git a/src/main/java/club/joylink/rtss/simulation/cbtc/data/support/RoutePath.java b/src/main/java/club/joylink/rtss/simulation/cbtc/data/support/RoutePath.java index c78eb813a..6e0d3783a 100644 --- a/src/main/java/club/joylink/rtss/simulation/cbtc/data/support/RoutePath.java +++ b/src/main/java/club/joylink/rtss/simulation/cbtc/data/support/RoutePath.java @@ -1,5 +1,6 @@ package club.joylink.rtss.simulation.cbtc.data.support; +import club.joylink.rtss.exception.BusinessExceptionAssertEnum; import club.joylink.rtss.simulation.cbtc.constant.RunLevel; import club.joylink.rtss.simulation.cbtc.data.map.*; import club.joylink.rtss.simulation.cbtc.exception.SimulationException; @@ -10,6 +11,7 @@ import org.springframework.util.CollectionUtils; import java.util.ArrayList; import java.util.List; import java.util.Objects; +import java.util.stream.Collectors; @Getter public class RoutePath { @@ -26,7 +28,10 @@ public class RoutePath { /** 信号机列表 */ private List signalList = new ArrayList<>(); - /** 区段列表 */ + /** 进路列表 */ + private List routeList = new ArrayList<>(); + + /** 区段列表(不包含start和end) */ private List
sectionList = new ArrayList<>(); /** 方向 */ @@ -48,15 +53,40 @@ public class RoutePath { } public void addSignal(Signal signal) { + if (this.signalList.contains(signal)) { + return; + } this.signalList.add(signal); } public void addSection(Section section) { + if (this.sectionList.contains(section)) { + return; + } this.sectionList.add(section); } public void addSections(List
sections) { - this.sectionList.addAll(sections); + if (!CollectionUtils.isEmpty(sections)) { + for (Section section : sections) { + this.addSection(section); + } + } + } + + public void addRoute(Route route) { + if (this.routeList.contains(route)) { + return; + } + this.routeList.add(route); + } + + public void addRoutes(List routeList) { + if (!CollectionUtils.isEmpty(routeList)) { + for (Route route : routeList) { + this.addRoute(route); + } + } } public RoutePath cloneNew() { @@ -73,9 +103,25 @@ public class RoutePath { return length; } float len = 0; + if (start.isFunctionTrack()) { + if (this.isRight()) { + len += start.getLen() - start.getStopPointRight(); + } else { + len += start.getStopPointLeft(); + } + } for (Section section : this.sectionList) { len += section.getLen(); } + if (end.isFunctionTrack()) { + if (this.isRight()) { + len += end.getStopPointRight(); + } else { + len += end.getLen() - end.getStopPointLeft(); + } + } else { + len += end.getLen(); + } this.length = len; return len; } @@ -85,7 +131,9 @@ public class RoutePath { } public boolean containsSection(Section section) { - return this.sectionList.contains(section) || Objects.equals(section, this.start); + return this.start.isSamePhysical(section.getCode()) || + this.end.isSamePhysical(section.getCode()) || + this.sectionList.contains(section); } public boolean isPathSection(Section section) { @@ -103,14 +151,7 @@ public class RoutePath { } return true; } - - public String debugStr() { - return String.format("%s(%s)->%s(%s)", - this.start.getStation().getName(), this.start.getName(), - this.end.getStation().getName(), this.end.getName()); - } - - public float getLenFromSection(Section fromSection){ + public float getLenFromSection(Section fromSection){ List
list = new ArrayList<>(); if(sectionList.contains(fromSection)){ int i = sectionList.indexOf(fromSection); @@ -128,6 +169,56 @@ public class RoutePath { } return len; } + + public SectionPosition getSectionPositionOfLen(float len) { + BusinessExceptionAssertEnum.SYSTEM_EXCEPTION.assertTrue(len <= this.length); + + float l = len; + Section section = null; + float offset = 0; + if (this.start.isFunctionTrack()) { + float s = 0; + if (this.isRight()) { + s = this.start.getLen() - this.start.getStopPointRight(); + } else { + s = this.start.getStopPointLeft(); + } + if (l < s) { + offset = this.start.getStopPointRight() + l; + section = this.start; + } else { + l -= s; + } + } + if (section == null) { + for (Section next : this.sectionList) { + if (l <= next.getLen()) { + section = next; + if (this.isRight()) { + offset = l; + } else { + offset = next.getLen() - l; + } + break; + } else { + l -= next.getLen(); + } + } + } + if (section == null) { + // end区段 + BusinessExceptionAssertEnum.SYSTEM_EXCEPTION.assertTrue(l <= this.end.getLen()); + section = this.end; + if (this.isRight()) { + offset = l; + } else { + offset = this.end.getLen() - l; + } + } + BusinessExceptionAssertEnum.SYSTEM_EXCEPTION.assertNotNull(section); + return new SectionPosition(section, offset); + } + public SectionPosition getSectionPositionOfLen(float runLen,Section fromSection) { float remain = runLen; Section target = null; @@ -242,4 +333,36 @@ public class RoutePath { } return false; } + + public Section getLastSection() { + return this.sectionList.get(this.sectionList.size() - 1); + } + + public String debugStr() { + return String.format("%s(%s)->%s(%s)", + this.start.getStation().getName(), this.start.getName(), + this.end.getStation().getName(), this.end.getName()); + } + + public String debugStr2() { + String sections = String.join(",", this.sectionList.stream() + .map(Section::debugStr) + .collect(Collectors.toList())); + String signals = String.join(",", this.signalList.stream() + .map(Signal::debugStr) + .collect(Collectors.toList())); + String routes = String.join(",", this.routeList.stream() + .map(Route::debugStr) + .collect(Collectors.toList())); + return String.format("进路路径[%s]:{方向:%s," + + "距离:%s" + + "途经区段:[%s]," + + "途经信号机:[%s]," + + "途经进路(多种方式):[%s]}", + this.debugStr(), this.isRight()?"右":"左", + this.length, + sections, + signals, + routes); + } }