客流策略——跳停策略逻辑开发
This commit is contained in:
parent
44965d8054
commit
99ddf2db15
@ -1,6 +1,7 @@
|
|||||||
package club.joylink.rtss.simulation.cbtc.data.plan;
|
package club.joylink.rtss.simulation.cbtc.data.plan;
|
||||||
|
|
||||||
import club.joylink.rtss.simulation.cbtc.data.map.Section;
|
import club.joylink.rtss.simulation.cbtc.data.map.Section;
|
||||||
|
import club.joylink.rtss.simulation.cbtc.data.map.Stand;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.map.Station;
|
import club.joylink.rtss.simulation.cbtc.data.map.Station;
|
||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
@ -356,4 +357,37 @@ public class TripPlan {
|
|||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isPassingStand(Stand stand) {
|
||||||
|
boolean passing = false;
|
||||||
|
for (StationPlan stationPlan : this.getPlanList()) {
|
||||||
|
if (Objects.equals(stationPlan.getSection(), stand.getSection())) {
|
||||||
|
passing = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return passing;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getPlanIndex(Section section) {
|
||||||
|
int index = -1;
|
||||||
|
for (int i = 0; i < this.planList.size(); i++) {
|
||||||
|
if (Objects.equals(this.planList.get(i).getSection(), section)) {
|
||||||
|
index = i;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return index;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getPlanIndex(String sectionCode) {
|
||||||
|
int index = -1;
|
||||||
|
for (int i = 0; i < this.planList.size(); i++) {
|
||||||
|
if (Objects.equals(this.planList.get(i).getSection().getCode(), sectionCode)) {
|
||||||
|
index = i;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return index;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -166,7 +166,9 @@ public class PassengerFlowSimulateService {
|
|||||||
|
|
||||||
private void sendTrainPassengerFlowData(Simulation simulation, Map<String, TrainPassengerFlow> trainPassengerFlowMap) {
|
private void sendTrainPassengerFlowData(Simulation simulation, Map<String, TrainPassengerFlow> trainPassengerFlowMap) {
|
||||||
List<Map<String, Object>> trainPFNumList = new ArrayList<>();
|
List<Map<String, Object>> trainPFNumList = new ArrayList<>();
|
||||||
for (TrainPassengerFlow flow : trainPassengerFlowMap.values()) {
|
List<TrainInfo> superviseTrainList = simulation.getRepository().getSuperviseTrainList();
|
||||||
|
for (TrainInfo trainInfo : superviseTrainList) {
|
||||||
|
TrainPassengerFlow flow = trainPassengerFlowMap.get(trainInfo.getGroupNumber());
|
||||||
Map<String, Object> trainPfNum = new HashMap<>();
|
Map<String, Object> trainPfNum = new HashMap<>();
|
||||||
trainPfNum.put("code", flow.getTrain().getGroupNumber());
|
trainPfNum.put("code", flow.getTrain().getGroupNumber());
|
||||||
trainPfNum.put("num", flow.getPassengerQuantity());
|
trainPfNum.put("num", flow.getPassengerQuantity());
|
||||||
|
@ -7,6 +7,8 @@ public final class Config {
|
|||||||
public static final int STRATEGY_CAL_TIME = 30;
|
public static final int STRATEGY_CAL_TIME = 30;
|
||||||
/** 站台大客流判断基准值 */
|
/** 站台大客流判断基准值 */
|
||||||
public static final int STAND_LPF_TRIGGER = 800;
|
public static final int STAND_LPF_TRIGGER = 800;
|
||||||
|
/** 站台可跳停的最大客流数 */
|
||||||
|
public static final int STAND_JUMP_MAX = 50;
|
||||||
/** 站台最大停站时间:单位 - 秒 */
|
/** 站台最大停站时间:单位 - 秒 */
|
||||||
public static final int STAND_MAX_STOP_TIME = 90;
|
public static final int STAND_MAX_STOP_TIME = 90;
|
||||||
/** 列车最大容量 */
|
/** 列车最大容量 */
|
||||||
|
@ -44,6 +44,7 @@ public class StrategyCalculateAndRecommendService implements ApplicationContextA
|
|||||||
}
|
}
|
||||||
for (Strategy strategy : list) {
|
for (Strategy strategy : list) {
|
||||||
strategyService.calculate(data.clone(), strategy);
|
strategyService.calculate(data.clone(), strategy);
|
||||||
|
strategy.buildDescription();
|
||||||
strategy.handleTarget();
|
strategy.handleTarget();
|
||||||
log.info(String.format("策略[%s]计算指标为:%s", strategy.getDescription(),
|
log.info(String.format("策略[%s]计算指标为:%s", strategy.getDescription(),
|
||||||
strategy.targetDebugStr()));
|
strategy.targetDebugStr()));
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
package club.joylink.rtss.simulation.cbtc.passenger.strategy.data;
|
package club.joylink.rtss.simulation.cbtc.passenger.strategy.data;
|
||||||
|
|
||||||
import club.joylink.rtss.simulation.cbtc.data.map.Stand;
|
import club.joylink.rtss.simulation.cbtc.data.map.Stand;
|
||||||
|
import club.joylink.rtss.simulation.cbtc.data.plan.TripPlan;
|
||||||
import com.fasterxml.jackson.annotation.JsonIgnore;
|
import com.fasterxml.jackson.annotation.JsonIgnore;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
|
|
||||||
@ -11,6 +12,11 @@ public class JumpStrategy extends Strategy {
|
|||||||
*/
|
*/
|
||||||
@JsonIgnore
|
@JsonIgnore
|
||||||
Stand stand;
|
Stand stand;
|
||||||
|
/**
|
||||||
|
* 是否已经计算过跳停
|
||||||
|
*/
|
||||||
|
@JsonIgnore
|
||||||
|
private boolean jumped;
|
||||||
private String groupNumber;
|
private String groupNumber;
|
||||||
/** 服务号 */
|
/** 服务号 */
|
||||||
String serviceNumber;
|
String serviceNumber;
|
||||||
@ -28,7 +34,16 @@ public class JumpStrategy extends Strategy {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String buildDescription() {
|
public String buildDescription() {
|
||||||
this.description = String.format("站台%s设置跳停", stand.debugStr());
|
this.description = String.format("为列车[%s-%s|%s],设置站台%s跳停",
|
||||||
|
groupNumber, serviceNumber, tripNumber,
|
||||||
|
stand.debugStr());
|
||||||
return this.description;
|
return this.description;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void jumpedByTrain(String groupNumber, TripPlan tripPlan) {
|
||||||
|
this.jumped = true;
|
||||||
|
this.groupNumber = groupNumber;
|
||||||
|
this.serviceNumber = tripPlan.getServiceNumber();
|
||||||
|
this.tripNumber = tripPlan.getTripNumber();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -18,7 +18,6 @@ public class ParkTimeStrategy extends Strategy {
|
|||||||
super(Type.PARK_TIME);
|
super(Type.PARK_TIME);
|
||||||
this.stand = stand;
|
this.stand = stand;
|
||||||
this.time = parkTime;
|
this.time = parkTime;
|
||||||
this.buildDescription();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public String getStandCode() {
|
public String getStandCode() {
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
package club.joylink.rtss.simulation.cbtc.passenger.strategy.data;
|
package club.joylink.rtss.simulation.cbtc.passenger.strategy.data;
|
||||||
|
|
||||||
|
import club.joylink.rtss.simulation.cbtc.data.map.Section;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.map.Stand;
|
import club.joylink.rtss.simulation.cbtc.data.map.Stand;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.plan.RealRun;
|
import club.joylink.rtss.simulation.cbtc.data.plan.RealRun;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.plan.TripPlan;
|
import club.joylink.rtss.simulation.cbtc.data.plan.TripPlan;
|
||||||
@ -30,6 +31,11 @@ public class StrategyCalculateData {
|
|||||||
|
|
||||||
Map<String, StandPassenger> standPassengerMap = new ConcurrentHashMap<>();
|
Map<String, StandPassenger> standPassengerMap = new ConcurrentHashMap<>();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 大客流站台
|
||||||
|
*/
|
||||||
|
List<StandPassenger> lpfStandList = new ArrayList<>();
|
||||||
|
|
||||||
List<Stand> leftStandList;
|
List<Stand> leftStandList;
|
||||||
|
|
||||||
List<Stand> rightStandList;
|
List<Stand> rightStandList;
|
||||||
@ -59,6 +65,9 @@ public class StrategyCalculateData {
|
|||||||
for (StandPassengerFlow standPassengerFlow : allStandPassengerFlow) {
|
for (StandPassengerFlow standPassengerFlow : allStandPassengerFlow) {
|
||||||
StandPassenger standPassenger = new StandPassenger(standPassengerFlow);
|
StandPassenger standPassenger = new StandPassenger(standPassengerFlow);
|
||||||
this.standPassengerMap.put(standPassenger.getStand().getCode(), standPassenger);
|
this.standPassengerMap.put(standPassenger.getStand().getCode(), standPassenger);
|
||||||
|
if (standPassenger.isLpf()) {
|
||||||
|
this.lpfStandList.add(standPassenger);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
List<Stand> leftList = new ArrayList<>();
|
List<Stand> leftList = new ArrayList<>();
|
||||||
List<Stand> rightList = new ArrayList<>();
|
List<Stand> rightList = new ArrayList<>();
|
||||||
@ -104,6 +113,9 @@ public class StrategyCalculateData {
|
|||||||
standPassengerMap.put(code, standPassenger.clone());
|
standPassengerMap.put(code, standPassenger.clone());
|
||||||
});
|
});
|
||||||
obj.standPassengerMap = standPassengerMap;
|
obj.standPassengerMap = standPassengerMap;
|
||||||
|
for (StandPassenger standPassenger : this.lpfStandList) {
|
||||||
|
obj.lpfStandList.add(standPassenger.clone());
|
||||||
|
}
|
||||||
obj.leftStandList = this.leftStandList;
|
obj.leftStandList = this.leftStandList;
|
||||||
obj.rightStandList = this.rightStandList;
|
obj.rightStandList = this.rightStandList;
|
||||||
List<TrainPassenger> tpList = new ArrayList<>();
|
List<TrainPassenger> tpList = new ArrayList<>();
|
||||||
@ -148,7 +160,11 @@ public class StrategyCalculateData {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
public RealRun queryPreviousRealRunData(String groupNumber) {
|
public List<RealRun> queryRealRuns(String groupNumber) {
|
||||||
|
return this.runMap.get(groupNumber);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RealRun queryLastRealRunData(String groupNumber) {
|
||||||
List<RealRun> realRuns = this.runMap.get(groupNumber);
|
List<RealRun> realRuns = this.runMap.get(groupNumber);
|
||||||
if (!CollectionUtils.isEmpty(realRuns)) {
|
if (!CollectionUtils.isEmpty(realRuns)) {
|
||||||
realRuns.sort(Comparator.comparing(RealRun::getTime));
|
realRuns.sort(Comparator.comparing(RealRun::getTime));
|
||||||
@ -180,4 +196,13 @@ public class StrategyCalculateData {
|
|||||||
public StandPassenger getStandPassengerByStand(Stand stand) {
|
public StandPassenger getStandPassengerByStand(Stand stand) {
|
||||||
return this.standPassengerMap.get(stand.getCode());
|
return this.standPassengerMap.get(stand.getCode());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isLpfStand(Section section) {
|
||||||
|
for (StandPassenger standPassenger : this.lpfStandList) {
|
||||||
|
if (Objects.equals(standPassenger.getStand().getSection(), section)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -5,6 +5,7 @@ import club.joylink.rtss.simulation.cbtc.data.map.Stand;
|
|||||||
import club.joylink.rtss.simulation.cbtc.data.plan.RealRun;
|
import club.joylink.rtss.simulation.cbtc.data.plan.RealRun;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.plan.StationPlan;
|
import club.joylink.rtss.simulation.cbtc.data.plan.StationPlan;
|
||||||
import club.joylink.rtss.simulation.cbtc.data.plan.TripPlan;
|
import club.joylink.rtss.simulation.cbtc.data.plan.TripPlan;
|
||||||
|
import club.joylink.rtss.simulation.cbtc.passenger.strategy.Config;
|
||||||
import club.joylink.rtss.simulation.cbtc.passenger.strategy.data.JumpStrategy;
|
import club.joylink.rtss.simulation.cbtc.passenger.strategy.data.JumpStrategy;
|
||||||
import club.joylink.rtss.simulation.cbtc.passenger.strategy.data.StandPassenger;
|
import club.joylink.rtss.simulation.cbtc.passenger.strategy.data.StandPassenger;
|
||||||
import club.joylink.rtss.simulation.cbtc.passenger.strategy.data.StrategyCalculateData;
|
import club.joylink.rtss.simulation.cbtc.passenger.strategy.data.StrategyCalculateData;
|
||||||
@ -13,8 +14,9 @@ import lombok.extern.slf4j.Slf4j;
|
|||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
import org.springframework.util.CollectionUtils;
|
import org.springframework.util.CollectionUtils;
|
||||||
|
|
||||||
import java.time.LocalTime;
|
import java.time.LocalDateTime;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Comparator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
|
|
||||||
@ -49,20 +51,217 @@ public class JumpStrategyServiceImpl implements StrategyService<JumpStrategy> {
|
|||||||
log.debug(String.format("第一个站,不生成跳停策略"));
|
log.debug(String.format("第一个站,不生成跳停策略"));
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
List<Stand> jumpableStandList = new ArrayList<>();
|
List<Stand> jumpableStandList;
|
||||||
if (right) {
|
if (right) {
|
||||||
jumpableStandList = rightStandList.subList(0, index);
|
jumpableStandList = rightStandList.subList(0, index);
|
||||||
} else {
|
} else {
|
||||||
jumpableStandList = leftStandList.subList(0, index);
|
jumpableStandList = leftStandList.subList(0, index);
|
||||||
}
|
}
|
||||||
List<TrainPassenger> trainPassengerList = data.getTrainPassengerList();
|
List<TrainPassenger> trainPassengerList = data.getTrainPassengerList();
|
||||||
|
for (int i = jumpableStandList.size()-1; i > 0; i--) { // 起始站不跳停
|
||||||
|
Stand s = jumpableStandList.get(i);
|
||||||
|
// 该站台人数是否支持跳停
|
||||||
|
StandPassenger sp = data.getStandPassengerByStand(s);
|
||||||
|
if (sp.getWait() >= Config.STAND_JUMP_MAX) {
|
||||||
|
log.debug(String.format("站台[%s]客流数[%s]>=站台跳停最大客流量[%s],不能跳停",
|
||||||
|
s.debugStr(), sp.getWait(), Config.STAND_JUMP_MAX));
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
// 该站是否被前列车跳过
|
||||||
|
// boolean jump = this.isJustJumped(data, s);
|
||||||
|
list.add(new JumpStrategy(s));
|
||||||
|
}
|
||||||
log.debug(String.format("生成跳停策略[%s]个", list.size()));
|
log.debug(String.format("生成跳停策略[%s]个", list.size()));
|
||||||
return list;
|
return list;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private boolean isJustJumped(StrategyCalculateData data, Stand stand) {
|
||||||
|
List<TrainPassenger> trainPassengerList = data.getTrainPassengerList();
|
||||||
|
List<RealRun> list = new ArrayList<>();
|
||||||
|
for (TrainPassenger trainPassenger : trainPassengerList) {
|
||||||
|
String groupNumber = trainPassenger.getGroupNumber();
|
||||||
|
TripPlan tripPlan = data.queryTripPlan(trainPassenger.getServiceNumber(), trainPassenger.getTripNumber());
|
||||||
|
if (tripPlan == null) {
|
||||||
|
log.warn(String.format("列车[%s-%s|%s]没有找到车次计划",
|
||||||
|
groupNumber, trainPassenger.getServiceNumber(), trainPassenger.getTripNumber()));
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
int index = tripPlan.getPlanIndex(stand.getSection());
|
||||||
|
if (index < 0) { // 没有对应站台计划,无需判断跳停
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
List<RealRun> realRunList = data.queryRealRuns(groupNumber);
|
||||||
|
if (!CollectionUtils.isEmpty(realRunList)) {
|
||||||
|
realRunList.sort(Comparator.comparing(RealRun::getTime));
|
||||||
|
RealRun last = realRunList.get(realRunList.size() - 1);
|
||||||
|
int lastRunIndex = tripPlan.getPlanIndex(last.getSectionCode());
|
||||||
|
if (lastRunIndex < index) { // 列车实际运行未过站台
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
RealRun jumpRun = this.isTrainJumpStand(trainPassenger, realRunList, stand);
|
||||||
|
if (jumpRun != null) {
|
||||||
|
list.add(jumpRun);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
private RealRun isTrainJumpStand(TrainPassenger trainPassenger, List<RealRun> realRunList, Stand stand) {
|
||||||
|
RealRun jumpRun = null;
|
||||||
|
boolean jump = true;
|
||||||
|
for (int i = realRunList.size() - 1; i >= 0; i--) {
|
||||||
|
RealRun realRun = realRunList.get(i);
|
||||||
|
if (!Objects.equals(realRun.getServiceNumber(), trainPassenger.getServiceNumber()) ||
|
||||||
|
!Objects.equals(realRun.getTripNumber(), trainPassenger.getTripNumber())) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (Objects.equals(realRun.getSectionCode(), stand.getSection().getCode())) {
|
||||||
|
if (!realRun.isArrive() && i > 0) {
|
||||||
|
RealRun pre = realRunList.get(i - 1);
|
||||||
|
if (Objects.equals(pre.getServiceNumber(), trainPassenger.getServiceNumber()) &&
|
||||||
|
Objects.equals(pre.getTripNumber(), trainPassenger.getTripNumber()) &&
|
||||||
|
Objects.equals(pre.getSectionCode(), stand.getSection().getCode())) {
|
||||||
|
jump = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (jump) {
|
||||||
|
jumpRun = realRun;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return jumpRun;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void calculate(StrategyCalculateData data, JumpStrategy strategy) {
|
public void calculate(StrategyCalculateData data, JumpStrategy strategy) {
|
||||||
|
List<TrainPassenger> trainPassengerList = data.getTrainPassengerList();
|
||||||
|
LocalDateTime systemTime = data.getSystemTime();
|
||||||
|
LocalDateTime startTime = systemTime;
|
||||||
|
LocalDateTime endTime = systemTime.plusMinutes(Config.STRATEGY_CAL_TIME);
|
||||||
|
boolean jump = false;
|
||||||
|
int i = 0;
|
||||||
|
while (startTime.isBefore(endTime) && i < 1000) {
|
||||||
|
++i;
|
||||||
|
LocalDateTime nextTime = null;
|
||||||
|
for (TrainPassenger trainPassenger : trainPassengerList) {
|
||||||
|
String groupNumber = trainPassenger.getGroupNumber();
|
||||||
|
List<RealRun> realRunList = data.queryRealRuns(groupNumber);
|
||||||
|
if (CollectionUtils.isEmpty(realRunList)) {
|
||||||
|
TripPlan tripPlan = data.queryTripPlan(trainPassenger.getServiceNumber(), trainPassenger.getTripNumber());
|
||||||
|
if (tripPlan == null) {
|
||||||
|
log.warn(String.format("列车[%s-%s|%s]没有找到车次计划",
|
||||||
|
groupNumber, trainPassenger.getServiceNumber(), trainPassenger.getTripNumber()));
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (tripPlan.isBackup()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
List<StationPlan> planList = tripPlan.getPlanList();
|
||||||
|
for (StationPlan stationPlan : planList) {
|
||||||
|
if (stationPlan.getArriveTime().compareTo(systemTime.toLocalTime()) >= 0) {
|
||||||
|
this.handleTrainRun(data, strategy, trainPassenger, tripPlan, stationPlan);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
realRunList = data.queryRealRuns(groupNumber);
|
||||||
|
if (CollectionUtils.isEmpty(realRunList)) {
|
||||||
|
log.error(String.format("列车[%s-%s|%s],车次[%s],时间[%s]",
|
||||||
|
groupNumber, trainPassenger.getServiceNumber(), trainPassenger.getTripNumber(),
|
||||||
|
tripPlan.debugStr(), systemTime.toString()));
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
RealRun lastRun = realRunList.get(realRunList.size() - 1);
|
||||||
|
TripPlan tripPlan = data.queryTripPlan(lastRun.getServiceNumber(), lastRun.getTripNumber());
|
||||||
|
StationPlan stationPlan = tripPlan.queryStationPlanByStationCode(lastRun.getStationCode());
|
||||||
|
BusinessExceptionAssertEnum.SYSTEM_EXCEPTION.assertNotNull(stationPlan);
|
||||||
|
if (lastRun.isArrive()) {
|
||||||
|
this.handleTrainRun(data, strategy, trainPassenger, tripPlan, stationPlan);
|
||||||
|
} else {
|
||||||
|
if (tripPlan.isLastPlan(stationPlan)) {
|
||||||
|
TripPlan nextTripPlan = data.queryNextTripPlan(tripPlan);
|
||||||
|
if (nextTripPlan != null) {
|
||||||
|
StationPlan nextStationPlan = nextTripPlan.getFirstStationPlan();
|
||||||
|
this.handleTrainRun(data, strategy, trainPassenger, nextTripPlan, nextStationPlan);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
StationPlan nextStationPlan = tripPlan.queryNextStationPlan(stationPlan.getStation());
|
||||||
|
this.handleTrainRun(data, strategy, trainPassenger, tripPlan, nextStationPlan);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// 更新nextTime
|
||||||
|
if (!CollectionUtils.isEmpty(realRunList)) {
|
||||||
|
RealRun last = realRunList.get(realRunList.size() - 1);
|
||||||
|
if (nextTime == null || nextTime.isAfter(last.getTime())) {
|
||||||
|
nextTime = last.getTime();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
systemTime = nextTime;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void handleTrainRun(StrategyCalculateData data,
|
||||||
|
JumpStrategy strategy,
|
||||||
|
TrainPassenger trainPassenger,
|
||||||
|
TripPlan tripPlan, StationPlan stationPlan) {
|
||||||
|
Stand stand = strategy.getStand();
|
||||||
|
String groupNumber = trainPassenger.getGroupNumber();
|
||||||
|
List<RealRun> realRunList = data.queryRealRuns(groupNumber);
|
||||||
|
RealRun lastRun = null;
|
||||||
|
int offset = 0;
|
||||||
|
if (!CollectionUtils.isEmpty(realRunList)) {
|
||||||
|
// 获取上一个实际运行,并计算时间偏移
|
||||||
|
lastRun = realRunList.get(realRunList.size() - 1);
|
||||||
|
TripPlan lastTripPlan = data.queryTripPlan(lastRun.getServiceNumber(), lastRun.getTripNumber());
|
||||||
|
StationPlan lastStationPlan = lastTripPlan.queryStationPlanByStationCode(lastRun.getStationCode());
|
||||||
|
if (lastRun.isArrive()) {
|
||||||
|
offset = lastRun.getTime().toLocalTime().toSecondOfDay() - lastStationPlan.getArriveTime().toSecondOfDay();
|
||||||
|
} else {
|
||||||
|
offset = lastRun.getTime().toLocalTime().toSecondOfDay() - lastStationPlan.getLeaveTime().toSecondOfDay();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (Objects.equals(stand.getSection(), stationPlan.getSection()) && !strategy.isJumped()) { // 跳停站台计划
|
||||||
|
// 跳停策略指定的跳停站台,构建跳停运行,并更新策略
|
||||||
|
RealRun passing = this.buildRealRun(groupNumber, tripPlan, stationPlan, false,
|
||||||
|
stationPlan.getArriveTime(), offset, data.getSystemTime());
|
||||||
|
data.addRealRun(passing);
|
||||||
|
strategy.jumpedByTrain(groupNumber, tripPlan);
|
||||||
|
strategy.addTarget1(-Config.TRAIN_PASS_SAVE_TIME);
|
||||||
|
StandPassenger standPassenger = data.getStandPassengerByStand(stand);
|
||||||
|
strategy.addTarget2(standPassenger.getWait());
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// 非跳停,根据计划更新预测运行
|
||||||
|
if (lastRun == null ||
|
||||||
|
!Objects.equals(stationPlan.getStation().getCode(), lastRun.getStationCode())) {
|
||||||
|
RealRun arrive = this.buildRealRun(groupNumber, tripPlan, stationPlan, true,
|
||||||
|
stationPlan.getArriveTime(), offset, data.getSystemTime());
|
||||||
|
data.addRealRun(arrive);
|
||||||
|
}
|
||||||
|
int parkTime = stationPlan.getParkTime();
|
||||||
|
// 列车到站乘客上车,更新列车上人数
|
||||||
|
if (stationPlan.getSection().getStandList().size() == 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
StandPassenger standPassenger = data.getStandPassengerByStand(stationPlan.getSection().getStandList().get(0));
|
||||||
|
int wait = standPassenger.getWait(); // 站台等待乘客数
|
||||||
|
float predict = (parkTime - Config.INVALID_BOARD_TIME) * Config.PASSENGER_BOARD_SPEED; // 根据停站预测的可上车人数
|
||||||
|
int remain = Config.TRAIN_CAPACITY - trainPassenger.getNum(); // 列车上剩余可载人数
|
||||||
|
float min = Math.min(Math.min(wait, predict), remain); // 实际上车人数
|
||||||
|
standPassenger.minus(min);
|
||||||
|
trainPassenger.plus(min);
|
||||||
|
// 大客流站计算指标
|
||||||
|
if (data.isLpfStand(stationPlan.getSection())) {
|
||||||
|
// 乘客等待时间(按人数统计,不考虑时间)
|
||||||
|
strategy.addTarget2(standPassenger.getWait());
|
||||||
|
}
|
||||||
|
// 生成预测实际运行图
|
||||||
|
RealRun leave = this.buildRealRun(trainPassenger.getGroupNumber(), tripPlan, stationPlan, false,
|
||||||
|
stationPlan.getLeaveTime(), offset, data.getSystemTime());
|
||||||
|
data.addRealRun(leave);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -70,18 +269,4 @@ public class JumpStrategyServiceImpl implements StrategyService<JumpStrategy> {
|
|||||||
return "跳停策略服务";
|
return "跳停策略服务";
|
||||||
}
|
}
|
||||||
|
|
||||||
private RealRun handleTrainLeave(StrategyCalculateData data, JumpStrategy strategy, TrainPassenger trainPassenger,
|
|
||||||
TripPlan tripPlan, StationPlan stationPlan, int offsetTime) {
|
|
||||||
Stand stand = strategy.getStand();
|
|
||||||
LocalTime arriveTime = stationPlan.getArriveTime();
|
|
||||||
LocalTime leaveTime = stationPlan.getLeaveTime();
|
|
||||||
// 生成预测实际运行图
|
|
||||||
RealRun leave = this.buildRealRun(trainPassenger.getGroupNumber(), tripPlan, stationPlan, false, leaveTime, offsetTime, data.getSystemTime());
|
|
||||||
data.addRealRun(leave);
|
|
||||||
// 大客流站计算指标
|
|
||||||
if (Objects.equals(stationPlan.getSection(), stand.getSection())) {
|
|
||||||
|
|
||||||
}
|
|
||||||
return leave;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
@ -78,7 +78,7 @@ public class ParkTimeStrategyServiceImpl implements StrategyService<ParkTimeStra
|
|||||||
// 上一实际到发
|
// 上一实际到发
|
||||||
RealRun realRun = trainPreviousMap.get(groupNumber);
|
RealRun realRun = trainPreviousMap.get(groupNumber);
|
||||||
if (realRun == null) {
|
if (realRun == null) {
|
||||||
realRun = data.queryPreviousRealRunData(groupNumber);
|
realRun = data.queryLastRealRunData(groupNumber);
|
||||||
if (realRun != null) {
|
if (realRun != null) {
|
||||||
trainPreviousMap.put(groupNumber, realRun);
|
trainPreviousMap.put(groupNumber, realRun);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user