按计划行车办理进路、解锁进路逻辑调整
进路路径筛选进路逻辑调整 直接办理进路道岔转动bug修改
This commit is contained in:
parent
55769ee2dc
commit
fc8f17cdb4
@ -39,6 +39,8 @@ import org.springframework.util.CollectionUtils;
|
|||||||
import java.time.LocalDateTime;
|
import java.time.LocalDateTime;
|
||||||
import java.time.LocalTime;
|
import java.time.LocalTime;
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
import java.util.function.Function;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
@Slf4j
|
@Slf4j
|
||||||
@Component
|
@Component
|
||||||
@ -400,16 +402,16 @@ public class AtsTrainLoadService {
|
|||||||
log.debug(String.format("实际加载列车数量:[%s]", loadedList.size()));
|
log.debug(String.format("实际加载列车数量:[%s]", loadedList.size()));
|
||||||
// 处理加载到折返轨的重叠列车
|
// 处理加载到折返轨的重叠列车
|
||||||
this.handleTurnBackCollisionTrainByTripPlan(simulation, loadedList);
|
this.handleTurnBackCollisionTrainByTripPlan(simulation, loadedList);
|
||||||
// 列车进路排列
|
|
||||||
this.setTrainRouteByTripPlan(simulation, loadedList);
|
|
||||||
// 重叠列车处理
|
// 重叠列车处理
|
||||||
this.handleCollision(simulation, loadedList);
|
this.handleCollision(simulation, loadedList);
|
||||||
// 车次计划发车状态
|
// 车次计划发车状态
|
||||||
this.updateTripPlanStatus(simulation);
|
this.updateTripPlanStatus(simulation);
|
||||||
// 列车上线并构建ATS监控列车信息
|
// 列车上线并构建ATS监控列车信息
|
||||||
this.trainOnlineAndBuildSupervise(simulation, loadedList);
|
List<TrainInfo> superviseList = this.trainOnlineAndBuildSupervise(simulation, loadedList);
|
||||||
// 办理ats选择的进路
|
// 列车进路排列
|
||||||
this.setRoutesThatSelectedByAts(simulation);
|
this.setTrainRouteByTripPlan(simulation, loadedList, superviseList);
|
||||||
|
// // 办理ats选择的进路
|
||||||
|
// this.setRoutesThatSelectedByAts(simulation);
|
||||||
// 计算移动授权
|
// 计算移动授权
|
||||||
// this.maService.calculateMaOfCtcTrains(simulation);
|
// this.maService.calculateMaOfCtcTrains(simulation);
|
||||||
// this.zcLogicLoop.run(simulation);
|
// this.zcLogicLoop.run(simulation);
|
||||||
@ -503,7 +505,8 @@ public class AtsTrainLoadService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void trainOnlineAndBuildSupervise(Simulation simulation, List<VirtualRealityTrain> loadedList) {
|
private List<TrainInfo> trainOnlineAndBuildSupervise(Simulation simulation, List<VirtualRealityTrain> loadedList) {
|
||||||
|
List<TrainInfo> superviseList = new ArrayList<>();
|
||||||
SimulationDataRepository repository = simulation.getRepository();
|
SimulationDataRepository repository = simulation.getRepository();
|
||||||
for (VirtualRealityTrain train : loadedList) {
|
for (VirtualRealityTrain train : loadedList) {
|
||||||
// 构建监控列车信息
|
// 构建监控列车信息
|
||||||
@ -555,8 +558,10 @@ public class AtsTrainLoadService {
|
|||||||
}
|
}
|
||||||
trainInfo.tracking(train);
|
trainInfo.tracking(train);
|
||||||
repository.addTrainInfo(trainInfo);
|
repository.addTrainInfo(trainInfo);
|
||||||
|
superviseList.add(trainInfo);
|
||||||
}
|
}
|
||||||
repository.addOnlineTrainList(loadedList);
|
repository.addOnlineTrainList(loadedList);
|
||||||
|
return superviseList;
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean isOnSectionStopPoint(SectionPosition headPosition, Section section, boolean right) {
|
private boolean isOnSectionStopPoint(SectionPosition headPosition, Section section, boolean right) {
|
||||||
@ -646,8 +651,16 @@ public class AtsTrainLoadService {
|
|||||||
return collisionList;
|
return collisionList;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void setTrainRouteByTripPlan(Simulation simulation, List<VirtualRealityTrain> loadedList) {
|
private void setTrainRouteByTripPlan(Simulation simulation, List<VirtualRealityTrain> loadedList, List<TrainInfo> superviseList) {
|
||||||
SimulationDataRepository repository = simulation.getRepository();
|
SimulationDataRepository repository = simulation.getRepository();
|
||||||
|
Map<String, TrainInfo> trainInfoMap = superviseList.stream()
|
||||||
|
.collect(Collectors.toMap(TrainInfo::getCode, Function.identity()));
|
||||||
|
// 按运行计划时间排序
|
||||||
|
loadedList.sort((train1, train2) -> {
|
||||||
|
TripPlan tripPlan1 = repository.getTripPlan(train1.getServiceNumber(), train1.getTripNumber());
|
||||||
|
TripPlan tripPlan2 = repository.getTripPlan(train2.getServiceNumber(), train2.getTripNumber());
|
||||||
|
return TripPlan.compare(tripPlan1, tripPlan2);
|
||||||
|
});
|
||||||
for (VirtualRealityTrain train : loadedList) {
|
for (VirtualRealityTrain train : loadedList) {
|
||||||
Section headSection = train.getHeadPosition().getSection();
|
Section headSection = train.getHeadPosition().getSection();
|
||||||
boolean right = train.isRight();
|
boolean right = train.isRight();
|
||||||
@ -658,20 +671,59 @@ public class AtsTrainLoadService {
|
|||||||
for (int i = 1; i < viaSectionList.size(); i++) {
|
for (int i = 1; i < viaSectionList.size(); i++) {
|
||||||
Section start = viaSectionList.get(i - 1);
|
Section start = viaSectionList.get(i - 1);
|
||||||
Section end = viaSectionList.get(i);
|
Section end = viaSectionList.get(i);
|
||||||
|
TrainInfo trainInfo = trainInfoMap.get(train.getCode());
|
||||||
|
if (trainInfo.getPlanStandTrack() == null) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (!end.getCode().equals(trainInfo.getPlanStandTrack())) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
Section tailSection = tailPosition.getSection();
|
||||||
// 取相邻两区段的路径单元,查询进路
|
// 取相邻两区段的路径单元,查询进路
|
||||||
RoutePath routePath = this.selectDefaultRoutePath(repository, start, end);
|
RoutePath routePath = this.selectDefaultRoutePath(repository, start, end);
|
||||||
Route route = routePath.queryRouteContainsSection(train.isCommunicable(), headSection, repository.getConfig());
|
if (!routePath.isPathSection(tailSection)) {
|
||||||
if (Objects.nonNull(route)) {
|
if (i - 2 >= 0) {
|
||||||
|
Section pre = viaSectionList.get(i - 2);
|
||||||
|
RoutePath preRoutePath = this.selectDefaultRoutePath(repository, pre, start);
|
||||||
|
Route route = preRoutePath.queryRouteContainsSection(train.isCommunicable(), tailSection, repository.getConfig());
|
||||||
|
if (route != null) {
|
||||||
// 排列好进路
|
// 排列好进路
|
||||||
this.deviceStatusModifyTool.openRouteDirect(simulation, route);
|
this.deviceStatusModifyTool.openRouteDirect(simulation, route);
|
||||||
// 根据列车位置直接进路正常解锁
|
// 根据列车位置直接进路正常解锁
|
||||||
this.deviceStatusModifyTool.routeUnlockByEndSection(route, tailPosition);
|
this.deviceStatusModifyTool.routeUnlockByEndSection(route, tailSection);
|
||||||
// 进路设置为正常解锁
|
}
|
||||||
this.ciLogic.trainUnlockStart(simulation, route);
|
}
|
||||||
route.setUnlockedSection(tailPosition.getSection());
|
}
|
||||||
|
List<Route> routeList = routePath.getRouteList();
|
||||||
|
Set<String> handledRouteStarts = new HashSet<>();
|
||||||
|
for (Route route : routeList) {
|
||||||
|
if (handledRouteStarts.contains(route.getStart().getCode())) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (route.isRouteSection(tailSection) || route.isRouteSection(headSection)) {
|
||||||
|
Route selected = routePath.selectDefaultRouteOfStart(route.getStart(), train.isCommunicable(), repository.getConfig());
|
||||||
|
if (selected != null) {
|
||||||
|
handledRouteStarts.add(route.getStart().getCode());
|
||||||
|
// 排列好进路
|
||||||
|
this.deviceStatusModifyTool.openRouteDirect(simulation, route);
|
||||||
|
// 根据列车位置直接进路正常解锁
|
||||||
|
Section unlockTo = tailSection;
|
||||||
|
if (!route.isRouteSection(tailSection)) {
|
||||||
|
unlockTo = headSection;
|
||||||
|
}
|
||||||
|
this.deviceStatusModifyTool.routeUnlockByEndSection(route, unlockTo);
|
||||||
|
}
|
||||||
|
} else if (!train.isStop() && route.getStart().isApproachSection(headSection.getCode())) {
|
||||||
|
// 排列好进路
|
||||||
|
Route aheadRoute = routePath.selectDefaultRouteOfStart(route.getStart(), train.isCommunicable(), repository.getConfig());
|
||||||
|
if (aheadRoute != null) {
|
||||||
|
this.deviceStatusModifyTool.openRouteDirect(simulation, aheadRoute);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -447,4 +447,42 @@ public class TripPlan {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 按计划时间先后顺序排序(对于同向的按到某个都达到的站的时间排序,对于不同向的默认向右在前)
|
||||||
|
* @param list
|
||||||
|
*/
|
||||||
|
public static void sort(List<TripPlan> list) {
|
||||||
|
list.sort(TripPlan::compare);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 比较车次计划先后顺序, 对于同向的按到某个都达到的站的时间排序,对于不同向的默认向右在前
|
||||||
|
* @param plan1
|
||||||
|
* @param plan2
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public static int compare(TripPlan plan1, TripPlan plan2) {
|
||||||
|
if (plan1.isRight() != plan2.isRight()) {
|
||||||
|
if (plan2.isRight()) {
|
||||||
|
return 1;
|
||||||
|
} else {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
List<StationPlan> spList1 = plan1.getPlanList();
|
||||||
|
List<StationPlan> spList2 = plan2.getPlanList();
|
||||||
|
StationPlan stationPlan1 = spList1.get(spList1.size() - 1);
|
||||||
|
StationPlan stationPlan2 = plan2.queryStationPlan(stationPlan1.getStation());
|
||||||
|
if (stationPlan2 != null) {
|
||||||
|
return stationPlan1.getArriveTime().compareTo(stationPlan2.getArriveTime());
|
||||||
|
}
|
||||||
|
stationPlan2 = spList2.get(spList2.size() - 1);
|
||||||
|
stationPlan1 = plan1.queryStationPlan(stationPlan2.getStation());
|
||||||
|
if (stationPlan1 != null) {
|
||||||
|
return stationPlan1.getArriveTime().compareTo(stationPlan2.getArriveTime());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return plan1.getStartTime().compareTo(plan2.getStartTime());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,7 +1,6 @@
|
|||||||
package club.joylink.rtss.simulation.cbtc.data.support;
|
package club.joylink.rtss.simulation.cbtc.data.support;
|
||||||
|
|
||||||
import club.joylink.rtss.exception.BusinessExceptionAssertEnum;
|
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.data.map.*;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import org.springframework.util.CollectionUtils;
|
import org.springframework.util.CollectionUtils;
|
||||||
@ -431,4 +430,57 @@ public class RoutePath {
|
|||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 根据始端信号机选择此进路路径所需的进路(对于哈尔滨的进路,根据通信和进路是否ATP判断,其他取延续保护默认定位进路)
|
||||||
|
* @param signal
|
||||||
|
* @param communicable
|
||||||
|
* @param config
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public Route selectDefaultRouteOfStart(Signal signal, boolean communicable, MapConfig config) {
|
||||||
|
List<Route> triggerList = new ArrayList<>();
|
||||||
|
for (Route route : this.routeList) {
|
||||||
|
if (config.isRouteLikeHa1()) {
|
||||||
|
if (communicable) { // 通信车找ATP进路
|
||||||
|
if (!route.isAtp()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
} else { // 非通信车找地面进路
|
||||||
|
if (!route.isGround()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (route.getStart().equals(signal) && !route.isTurnBack() &&
|
||||||
|
!triggerList.contains(route) && route.isAtsControl()) {
|
||||||
|
if (config.isRouteLikeHa1()) {
|
||||||
|
if (communicable && route.isAtp()) {
|
||||||
|
triggerList.add(route);
|
||||||
|
} else if (!communicable && route.isGround()) {
|
||||||
|
triggerList.add(route);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
triggerList.add(route);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
//选择要触发的进路
|
||||||
|
Route route = null;
|
||||||
|
if (triggerList.size() == 1) {
|
||||||
|
route = triggerList.get(0);
|
||||||
|
} else if (triggerList.size() > 1) {
|
||||||
|
// 取第一个延续保护道岔定位的
|
||||||
|
for (Route temp : triggerList) {
|
||||||
|
List<SwitchElement> switchList = temp.getOverlap().getFirstPath().getSwitchList();
|
||||||
|
if (switchList.get(0).isNormal()) {
|
||||||
|
route = temp;
|
||||||
|
break;
|
||||||
|
} else {
|
||||||
|
route = temp;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return route;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -7,7 +7,6 @@ import club.joylink.rtss.simulation.cbtc.constant.SignalAspect;
|
|||||||
import club.joylink.rtss.simulation.cbtc.constant.SwitchIndication;
|
import club.joylink.rtss.simulation.cbtc.constant.SwitchIndication;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.SimulationDataRepository;
|
import club.joylink.rtss.simulation.cbtc.data.SimulationDataRepository;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.map.*;
|
import club.joylink.rtss.simulation.cbtc.data.map.*;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.support.SectionPosition;
|
|
||||||
import club.joylink.rtss.simulation.cbtc.data.vr.VirtualRealitySignal;
|
import club.joylink.rtss.simulation.cbtc.data.vr.VirtualRealitySignal;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.vr.VirtualRealitySwitch;
|
import club.joylink.rtss.simulation.cbtc.data.vr.VirtualRealitySwitch;
|
||||||
import club.joylink.rtss.simulation.cbtc.device.virtual.VirtualRealityDeviceService;
|
import club.joylink.rtss.simulation.cbtc.device.virtual.VirtualRealityDeviceService;
|
||||||
@ -17,7 +16,6 @@ import org.springframework.stereotype.Component;
|
|||||||
import org.springframework.util.CollectionUtils;
|
import org.springframework.util.CollectionUtils;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collections;
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
|
|
||||||
@ -183,7 +181,7 @@ public class DeviceStatusModifyTool {
|
|||||||
virtualSwitch.finish();
|
virtualSwitch.finish();
|
||||||
aSwitch.setPos(SwitchIndication.N);
|
aSwitch.setPos(SwitchIndication.N);
|
||||||
} else {
|
} else {
|
||||||
virtualSwitch.control(VirtualRealitySwitch.Operation.NP);
|
virtualSwitch.control(VirtualRealitySwitch.Operation.RP);
|
||||||
virtualSwitch.finish();
|
virtualSwitch.finish();
|
||||||
aSwitch.setPos(SwitchIndication.R);
|
aSwitch.setPos(SwitchIndication.R);
|
||||||
}
|
}
|
||||||
@ -207,34 +205,20 @@ public class DeviceStatusModifyTool {
|
|||||||
* 直接根据最后一根区段解锁进路
|
* 直接根据最后一根区段解锁进路
|
||||||
* @param route
|
* @param route
|
||||||
*/
|
*/
|
||||||
public void routeUnlockByEndSection(Route route, SectionPosition tailPosition) {
|
public void routeUnlockByEndSection(Route route, Section tailSection) {
|
||||||
Section endOccupied = tailPosition.getSection();
|
if (!route.isRouteSection(tailSection)) {
|
||||||
if (!route.isRouteSection(endOccupied)) {
|
|
||||||
// 不是进路区段,不解锁
|
// 不是进路区段,不解锁
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
route.startNormalUnlock();
|
||||||
|
// 关闭始端信号机
|
||||||
|
openSignalDirectly(route.getStart(), route.getStart().getSignalModel().getDefaultAspect());
|
||||||
boolean right = route.getStart().isRight();
|
boolean right = route.getStart().isRight();
|
||||||
// 区段是顺序的(否则会有问题)
|
// 区段是顺序的(否则会有问题)
|
||||||
List<Section> sectionList = route.getSectionList();
|
List<Section> sectionList = route.getSectionList();
|
||||||
for (Section section : sectionList) {
|
for (Section section : sectionList) {
|
||||||
if (section.isSamePhysical(endOccupied.getCode())) {
|
if (section.isSamePhysical(tailSection.getCode())) {
|
||||||
if (!CollectionUtils.isEmpty(section.getLogicList())) {
|
route.updateUnlockedSection(tailSection);
|
||||||
// 逻辑区段占用,根据逻辑区段占用位置解锁
|
|
||||||
List<Section> logicList = section.getLogicList();
|
|
||||||
if (!right) { // 向左,逻辑区段列表reverse
|
|
||||||
logicList = new ArrayList<>(section.getLogicList());
|
|
||||||
Collections.reverse(logicList);
|
|
||||||
}
|
|
||||||
Section logicSection = tailPosition.getLogicSection();
|
|
||||||
for (Section logic : logicList) {
|
|
||||||
if (logic.equals(logicSection)) {
|
|
||||||
break;
|
|
||||||
} else {
|
|
||||||
logic.routeUnlocking(route);
|
|
||||||
logic.overlapUnlocking();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
// 直接解锁区段
|
// 直接解锁区段
|
||||||
|
Loading…
Reference in New Issue
Block a user