KPI优化

parent 365ed564
...@@ -2,6 +2,7 @@ package com.aps.entity.Algorithm; ...@@ -2,6 +2,7 @@ package com.aps.entity.Algorithm;
import com.aps.entity.Algorithm.IDAndChildID.GroupResult; import com.aps.entity.Algorithm.IDAndChildID.GroupResult;
import com.aps.entity.basic.Entry; import com.aps.entity.basic.Entry;
import com.aps.entity.basic.GlobalParam;
import com.aps.entity.basic.Machine; import com.aps.entity.basic.Machine;
import com.aps.entity.basic.Material; import com.aps.entity.basic.Material;
import com.aps.entity.basic.Order; import com.aps.entity.basic.Order;
...@@ -127,6 +128,8 @@ public class Chromosome { ...@@ -127,6 +128,8 @@ public class Chromosome {
private ObjectiveWeights objectiveWeights; private ObjectiveWeights objectiveWeights;
private GlobalParam globalParamSnapshot;
private TreeMap<String, Material> materials = new TreeMap<>(); private TreeMap<String, Material> materials = new TreeMap<>();
// private List<Material> materials = new ArrayList<>(); // private List<Material> materials = new ArrayList<>();
......
...@@ -80,7 +80,6 @@ public class GlobalParam { ...@@ -80,7 +80,6 @@ public class GlobalParam {
public static final String OBJECTIVE_SETUP_TIME = "setupTime"; // 总换型时间 public static final String OBJECTIVE_SETUP_TIME = "setupTime"; // 总换型时间
public static final String OBJECTIVE_MACHINE_LOAD = "machineLoad"; // 机器负载均衡 public static final String OBJECTIVE_MACHINE_LOAD = "machineLoad"; // 机器负载均衡
public static final String OBJECTIVE_TARDINESS = "tardiness"; // 延迟时间 public static final String OBJECTIVE_TARDINESS = "tardiness"; // 延迟时间
public static final String OBJECTIVE_SEMI_JIT = "semiJitSlack"; // 半成品提前完工惩罚
/// <summary> /// <summary>
/// 构造函数,初始化默认值 /// 构造函数,初始化默认值
...@@ -93,7 +92,6 @@ public class GlobalParam { ...@@ -93,7 +92,6 @@ public class GlobalParam {
objectiveConfigs.add(createMinimizeObjectiveConfig(OBJECTIVE_SETUP_TIME, 2, 0.39)); objectiveConfigs.add(createMinimizeObjectiveConfig(OBJECTIVE_SETUP_TIME, 2, 0.39));
objectiveConfigs.add(createMinimizeObjectiveConfig(OBJECTIVE_MACHINE_LOAD, 1, 0.3)); objectiveConfigs.add(createMinimizeObjectiveConfig(OBJECTIVE_MACHINE_LOAD, 1, 0.3));
objectiveConfigs.add(createMinimizeObjectiveConfig(OBJECTIVE_TARDINESS, 1, 0.3)); objectiveConfigs.add(createMinimizeObjectiveConfig(OBJECTIVE_TARDINESS, 1, 0.3));
objectiveConfigs.add(createMinimizeObjectiveConfig(OBJECTIVE_SEMI_JIT, 2, 0.01));
objectiveConfigs.sort(Comparator.comparing((ObjectiveConfig op) -> op.getLevel())); objectiveConfigs.sort(Comparator.comparing((ObjectiveConfig op) -> op.getLevel()));
} }
...@@ -191,4 +189,213 @@ public class GlobalParam { ...@@ -191,4 +189,213 @@ public class GlobalParam {
public void removeObjectiveConfig(String name) { public void removeObjectiveConfig(String name) {
objectiveConfigs.removeIf(config -> config.getName().equals(name)); objectiveConfigs.removeIf(config -> config.getName().equals(name));
} }
public void applyKpiConfig(Object rawConfig) {
List<?> kpiList = extractKpiList(rawConfig);
if (kpiList.isEmpty()) {
return;
}
List<ObjectiveConfig> configs = new ArrayList<>();
int sequence = 1;
for (Object item : kpiList) {
ObjectiveConfig config = toObjectiveConfig(item, sequence++);
if (config != null) {
configs.add(config);
}
}
if (!configs.isEmpty()) {
configs.sort(Comparator.comparing((ObjectiveConfig op) -> op.getLevel()));
objectiveConfigs = configs;
}
}
public GlobalParam copy() {
GlobalParam target = new GlobalParam();
target.IsBreakPriority = this.IsBreakPriority;
target.IsMultipleMachine = this.IsMultipleMachine;
target.IsUseCalendar = this.IsUseCalendar;
target.IsCheckMp = this.IsCheckMp;
target.IsCheckSf = this.IsCheckSf;
target.IsOverlap = this.IsOverlap;
target.isJit = this.isJit;
target._smoothSetup = this._smoothSetup;
target._smoothChangeOver = this._smoothChangeOver;
target._smoothChangeOverInWeek = this._smoothChangeOverInWeek;
target.pureNSGAIIMode = this.pureNSGAIIMode;
target.semiJitBufferMinutes = this.semiJitBufferMinutes;
target.materialSolveMaxIterations = this.materialSolveMaxIterations;
target.objectiveConfigs = copyObjectiveConfigs(this.objectiveConfigs);
return target;
}
private List<?> extractKpiList(Object rawConfig) {
if (rawConfig instanceof List) {
return (List<?>) rawConfig;
}
if (rawConfig instanceof Map) {
Map<?, ?> map = (Map<?, ?>) rawConfig;
Object kpiConfig = map.get("kpiConfig");
if (kpiConfig instanceof List) {
return (List<?>) kpiConfig;
}
Object kpiList = map.get("kpiList");
if (kpiList instanceof List) {
return (List<?>) kpiList;
}
}
return Collections.emptyList();
}
private ObjectiveConfig toObjectiveConfig(Object raw, int sequence) {
if (raw instanceof ObjectiveConfig) {
ObjectiveConfig source = (ObjectiveConfig) raw;
ObjectiveConfig copy = copyObjectiveConfig(source);
copy.setName(normalizeObjectiveName(copy.getName()));
return isKnownObjective(copy.getName()) ? copy : null;
}
if (!(raw instanceof Map)) {
return null;
}
Map<?, ?> map = (Map<?, ?>) raw;
String name = normalizeObjectiveName(asString(firstValue(map, "name", "code", "fieldName")));
if (!isKnownObjective(name)) {
return null;
}
ObjectiveConfig fallback = getObjectiveConfig(name);
ObjectiveConfig config = fallback == null ? createMinimizeObjectiveConfig(name, sequence, 1D) : copyObjectiveConfig(fallback);
config.setName(name);
config.setEnabled(asBoolean(firstValue(map, "enabled", "value"), config.isEnabled()));
config.setMinimize(asBoolean(firstValue(map, "isMinimize", "minimize"), config.isMinimize()));
config.setLevel(asInt(firstValue(map, "level", "sort"), config.getLevel()));
config.setWeight(asDouble(firstValue(map, "weight"), config.getWeight()));
config.setVal(asDouble(firstValue(map, "val", "valueNumber"), config.getVal()));
return config;
}
private List<ObjectiveConfig> copyObjectiveConfigs(List<ObjectiveConfig> source) {
if (source == null) {
return new ArrayList<>();
}
List<ObjectiveConfig> copy = new ArrayList<>();
for (ObjectiveConfig config : source) {
ObjectiveConfig copied = copyObjectiveConfig(config);
if (isKnownObjective(copied.getName())) {
copy.add(copied);
}
}
return copy;
}
private ObjectiveConfig copyObjectiveConfig(ObjectiveConfig source) {
ObjectiveConfig copy = new ObjectiveConfig();
if (source != null) {
copy.setName(source.getName());
copy.setEnabled(source.isEnabled());
copy.setMinimize(source.isMinimize());
copy.setLevel(source.getLevel());
copy.setWeight(source.getWeight());
copy.setVal(source.getVal());
}
return copy;
}
private Object firstValue(Map<?, ?> map, String... keys) {
for (String key : keys) {
if (map.containsKey(key)) {
return map.get(key);
}
}
return null;
}
private String normalizeObjectiveName(String name) {
if (name == null) {
return null;
}
String normalized = name.trim().replace("_", "").replace("-", "").replace(" ", "").toLowerCase(Locale.ROOT);
switch (normalized) {
case "makespan":
return OBJECTIVE_MAKESPAN;
case "flowtime":
case "totalflowtime":
return OBJECTIVE_FLOW_TIME;
case "setuptime":
case "totalsetuptime":
case "changeovertime":
return OBJECTIVE_SETUP_TIME;
case "machineload":
case "machineloadbalance":
case "loadbalance":
return OBJECTIVE_MACHINE_LOAD;
case "tardiness":
case "delaytime":
return OBJECTIVE_TARDINESS;
default:
return name.trim();
}
}
private boolean isKnownObjective(String name) {
return OBJECTIVE_MAKESPAN.equals(name)
|| OBJECTIVE_FLOW_TIME.equals(name)
|| OBJECTIVE_SETUP_TIME.equals(name)
|| OBJECTIVE_MACHINE_LOAD.equals(name)
|| OBJECTIVE_TARDINESS.equals(name);
}
private String asString(Object value) {
return value == null ? null : String.valueOf(value);
}
private boolean asBoolean(Object value, boolean defaultValue) {
if (value == null) {
return defaultValue;
}
if (value instanceof Boolean) {
return (Boolean) value;
}
if (value instanceof Number) {
return ((Number) value).intValue() != 0;
}
String text = String.valueOf(value).trim();
if ("1".equals(text)) {
return true;
}
if ("0".equals(text)) {
return false;
}
return text.isEmpty() ? defaultValue : Boolean.parseBoolean(text);
}
private int asInt(Object value, int defaultValue) {
if (value == null) {
return defaultValue;
}
if (value instanceof Number) {
return ((Number) value).intValue();
}
try {
return Integer.parseInt(String.valueOf(value).trim());
} catch (Exception e) {
return defaultValue;
}
}
private double asDouble(Object value, double defaultValue) {
if (value == null) {
return defaultValue;
}
if (value instanceof Number) {
return ((Number) value).doubleValue();
}
try {
return Double.parseDouble(String.valueOf(value).trim());
} catch (Exception e) {
return defaultValue;
}
}
} }
...@@ -2799,11 +2799,6 @@ if(geneDetails!=null&&geneDetails.size()>0) ...@@ -2799,11 +2799,6 @@ if(geneDetails!=null&&geneDetails.size()>0)
chromosome.setMachineLoadStd(machineLoadBalance); chromosome.setMachineLoadStd(machineLoadBalance);
Objectives[i] = machineLoadBalance; Objectives[i] = machineLoadBalance;
} }
if (GlobalParam.OBJECTIVE_SEMI_JIT.equals(config.getName())) {
double semiJitSlack = calculateSemiJitSlack(chromosome);
chromosome.setSemiJitSlack(semiJitSlack);
Objectives[i] = semiJitSlack;
}
i++; i++;
} }
} }
...@@ -2863,26 +2858,6 @@ if(geneDetails!=null&&geneDetails.size()>0) ...@@ -2863,26 +2858,6 @@ if(geneDetails!=null&&geneDetails.size()>0)
return Math.sqrt(variance)/avgUtilization ; return Math.sqrt(variance)/avgUtilization ;
} }
private double calculateSemiJitSlack(Chromosome chromosome) {
Map<Integer, GAScheduleResult> resultByOperation = chromosome.getResult().stream()
.collect(Collectors.toMap(GAScheduleResult::getOperationId, t -> t, (left, right) -> left));
double semiJitSlack = 0;
for (Entry operation : chromosome.getAllOperations()) {
if (operation.getLatestCompletionTime() == null) {
continue;
}
GAScheduleResult result = resultByOperation.get(operation.getId());
if (result == null) {
continue;
}
LocalDateTime completionTime = baseTime.plusSeconds(result.getEndTime());
if (completionTime.isBefore(operation.getLatestCompletionTime())) {
semiJitSlack += ChronoUnit.MINUTES.between(completionTime, operation.getLatestCompletionTime());
}
}
return semiJitSlack;
}
/** /**
* 补全:创建缓存键(核心逻辑,需与原 C# CreateCacheKey 一致) * 补全:创建缓存键(核心逻辑,需与原 C# CreateCacheKey 一致)
* 思路:将染色体的核心特征(机器选择+工序排序)拼接为字符串,确保相同染色体生成相同键 * 思路:将染色体的核心特征(机器选择+工序排序)拼接为字符串,确保相同染色体生成相同键
......
...@@ -167,10 +167,19 @@ public class PlanResultService { ...@@ -167,10 +167,19 @@ public class PlanResultService {
// 兼容旧调用:前端只传 sceneId 时,仍然会在内部根据场景创建人查找用户策略。 // 兼容旧调用:前端只传 sceneId 时,仍然会在内部根据场景创建人查找用户策略。
/**
* 只传场景ID时的排产入口。
* 这里不强制要求前端传 userId / baseRuleId / userRuleId,
* 后续会按场景创建人自动回退到可用的策略配置。
*/
public Chromosome execute2(String SceneId) { public Chromosome execute2(String SceneId) {
return execute2(SceneId, null, null, null); return execute2(SceneId, null, null, null);
} }
/**
* 完整排产入口。
* 传入的用户策略参数可选,缺省时会根据场景信息去找当前有效策略。
*/
public Chromosome execute2(String SceneId, Long userId, Long baseRuleId, String userRuleId) { public Chromosome execute2(String SceneId, Long userId, Long baseRuleId, String userRuleId) {
try { try {
...@@ -195,7 +204,7 @@ public class PlanResultService { ...@@ -195,7 +204,7 @@ public class PlanResultService {
List<ProdLaunchOrder> ProdLaunchOrders= _prodLaunchOrderService.lambdaQuery() List<ProdLaunchOrder> ProdLaunchOrders= _prodLaunchOrderService.lambdaQuery()
.eq(ProdLaunchOrder::getSceneId,SceneId) .eq(ProdLaunchOrder::getSceneId,SceneId)
.list(); .list();
GlobalParam globalParam=InitGlobalParam(); GlobalParam globalParam = buildInitialGlobalParam(SceneId, effectiveUserId, baseRuleId, userRuleId);
// 3. 创建调度服务 // 3. 创建调度服务
MachineSchedulerService machineScheduler = new MachineSchedulerService( MachineSchedulerService machineScheduler = new MachineSchedulerService(
...@@ -274,6 +283,7 @@ public class PlanResultService { ...@@ -274,6 +283,7 @@ public class PlanResultService {
// 这里会从 Dispatch 表加载锁定期工单,并添加到 chromosome.result 中 // 这里会从 Dispatch 表加载锁定期工单,并添加到 chromosome.result 中
lockedOrderProcessorService.addLockedOrdersToResult(chromosome); lockedOrderProcessorService.addLockedOrdersToResult(chromosome);
saveGlobalParamSnapshot(chromosome, globalParam);
boolean saved = _sceneService.saveChromosomeToFile(chromosome, SceneId); boolean saved = _sceneService.saveChromosomeToFile(chromosome, SceneId);
if (!saved) { if (!saved) {
throw new BusinessException("排产计算结果保存失败,请稍后重试或联系管理员"); throw new BusinessException("排产计算结果保存失败,请稍后重试或联系管理员");
...@@ -1118,7 +1128,7 @@ public class PlanResultService { ...@@ -1118,7 +1128,7 @@ public class PlanResultService {
.forEach(opInfo -> opInfo.setOp(operation)); .forEach(opInfo -> opInfo.setOp(operation));
} }
} }
GlobalParam globalParam=new GlobalParam(); GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
// Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); // Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
...@@ -1213,7 +1223,7 @@ public class PlanResultService { ...@@ -1213,7 +1223,7 @@ public class PlanResultService {
.filter(opInfo -> opInfo.getOp() != null && opInfo.getOp().getId() == operation.getId()) .filter(opInfo -> opInfo.getOp() != null && opInfo.getOp().getId() == operation.getId())
.forEach(opInfo -> opInfo.setOp(operation)); .forEach(opInfo -> opInfo.setOp(operation));
} }
GlobalParam globalParam=new GlobalParam(); GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
ScheduleOperationService ScheduleOperation=new ScheduleOperationService(materialRequirementService,this); ScheduleOperationService ScheduleOperation=new ScheduleOperationService(materialRequirementService,this);
ScheduleOperation.editMachineOption(chromosome,operation,operation.getSelectMachineID(),globalParam); ScheduleOperation.editMachineOption(chromosome,operation,operation.getSelectMachineID(),globalParam);
...@@ -1303,7 +1313,7 @@ public class PlanResultService { ...@@ -1303,7 +1313,7 @@ public class PlanResultService {
* 重新解码染色体 * 重新解码染色体
*/ */
private Chromosome redecodeChromosome(Chromosome chromosome,String SceneId) { private Chromosome redecodeChromosome(Chromosome chromosome,String SceneId) {
GlobalParam globalParam = new GlobalParam(); GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
ScheduleOperationService scheduleOperation = new ScheduleOperationService(materialRequirementService,this); ScheduleOperationService scheduleOperation = new ScheduleOperationService(materialRequirementService,this);
scheduleOperation.redecode(chromosome, chromosome.getBaseTime(), globalParam); scheduleOperation.redecode(chromosome, chromosome.getBaseTime(), globalParam);
// _sceneService.saveChromosomeToFile(chromosome, SceneId); // _sceneService.saveChromosomeToFile(chromosome, SceneId);
...@@ -1319,7 +1329,7 @@ public class PlanResultService { ...@@ -1319,7 +1329,7 @@ public class PlanResultService {
chromosome.setBaseTime(BaseTime); chromosome.setBaseTime(BaseTime);
ScheduleOperationService ScheduleOperation=new ScheduleOperationService(materialRequirementService,this); ScheduleOperationService ScheduleOperation=new ScheduleOperationService(materialRequirementService,this);
GlobalParam globalParam=new GlobalParam(); GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
ScheduleOperation.redecode(chromosome,chromosome.getBaseTime(), globalParam); ScheduleOperation.redecode(chromosome,chromosome.getBaseTime(), globalParam);
return chromosome; return chromosome;
...@@ -1328,8 +1338,8 @@ public class PlanResultService { ...@@ -1328,8 +1338,8 @@ public class PlanResultService {
Long newMachineId) { Long newMachineId) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
// 拖拽前清理历史工单在设备上的静态占位段,确保历史工单移动后可释放产能 // 拖拽前清理历史工单在设备上的静态占位段,确保历史工单移动后可释放产能
int releasedCount = releaseLockedOccupancyForDrag(chromosome); int releasedCount = releaseLockedOccupancyForDrag(chromosome);
...@@ -1470,7 +1480,7 @@ public class PlanResultService { ...@@ -1470,7 +1480,7 @@ public class PlanResultService {
LocalDateTime anchorTime = baseTime.plusSeconds(Math.max(freezeSeconds, 0L)); LocalDateTime anchorTime = baseTime.plusSeconds(Math.max(freezeSeconds, 0L));
// 5. 自动插单(占位后推 + 空挡前移) // 5. 自动插单(占位后推 + 空挡前移)
GlobalParam globalParam = InitGlobalParam(); GlobalParam globalParam = buildGlobalParamFromSnapshot(sceneId, chromosome, true);
ScheduleOperationService scheduleOperation = new ScheduleOperationService(materialRequirementService, this); ScheduleOperationService scheduleOperation = new ScheduleOperationService(materialRequirementService, this);
scheduleOperation.InsertOrderAuto( scheduleOperation.InsertOrderAuto(
chromosome, chromosome,
...@@ -1493,8 +1503,8 @@ public class PlanResultService { ...@@ -1493,8 +1503,8 @@ public class PlanResultService {
Long newMachineId,int lockStartTime) { Long newMachineId,int lockStartTime) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
// WriteScheduleSummary(chromosome); // WriteScheduleSummary(chromosome);
...@@ -1514,7 +1524,7 @@ public class PlanResultService { ...@@ -1514,7 +1524,7 @@ public class PlanResultService {
Long newMachineId,int lockStartTime) { Long newMachineId,int lockStartTime) {
GlobalParam globalParam=new GlobalParam(); GlobalParam globalParam = buildGlobalParamFromSnapshot(chromosome);
...@@ -1535,7 +1545,7 @@ public class PlanResultService { ...@@ -1535,7 +1545,7 @@ public class PlanResultService {
// WriteScheduleSummary(chromosome); // WriteScheduleSummary(chromosome);
GlobalParam globalParam=new GlobalParam(); GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
ScheduleOperation.redecode(chromosome, chromosome.getBaseTime(), globalParam); ScheduleOperation.redecode(chromosome, chromosome.getBaseTime(), globalParam);
// WriteScheduleSummary(chromosome); // WriteScheduleSummary(chromosome);
} }
...@@ -1544,9 +1554,8 @@ public class PlanResultService { ...@@ -1544,9 +1554,8 @@ public class PlanResultService {
public Chromosome SpiltOperation(String SceneId,int opId,Double[] splitCounts) { public Chromosome SpiltOperation(String SceneId,int opId,Double[] splitCounts) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
//this.baseTime=param.getBaseTime(); //this.baseTime=param.getBaseTime();
// WriteScheduleSummary(chromosome); // WriteScheduleSummary(chromosome);
...@@ -1561,9 +1570,8 @@ public class PlanResultService { ...@@ -1561,9 +1570,8 @@ public class PlanResultService {
public Chromosome DelOperation(String SceneId,int opId) { public Chromosome DelOperation(String SceneId,int opId) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
//this.baseTime=param.getBaseTime(); //this.baseTime=param.getBaseTime();
// WriteScheduleSummary(chromosome); // WriteScheduleSummary(chromosome);
...@@ -1578,9 +1586,8 @@ public class PlanResultService { ...@@ -1578,9 +1586,8 @@ public class PlanResultService {
public Chromosome DelOrder(String SceneId,String orderId) { public Chromosome DelOrder(String SceneId,String orderId) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
//this.baseTime=param.getBaseTime(); //this.baseTime=param.getBaseTime();
// WriteScheduleSummary(chromosome); // WriteScheduleSummary(chromosome);
...@@ -1598,9 +1605,8 @@ public class PlanResultService { ...@@ -1598,9 +1605,8 @@ public class PlanResultService {
public Chromosome LockOperation(String SceneId,int opId,boolean isLocked) { public Chromosome LockOperation(String SceneId,int opId,boolean isLocked) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
//this.baseTime=param.getBaseTime(); //this.baseTime=param.getBaseTime();
// WriteScheduleSummary(chromosome); // WriteScheduleSummary(chromosome);
...@@ -1615,9 +1621,8 @@ public class PlanResultService { ...@@ -1615,9 +1621,8 @@ public class PlanResultService {
public Chromosome SpiltOrder(String SceneId,String orderId,Double[] splitCounts) { public Chromosome SpiltOrder(String SceneId,String orderId,Double[] splitCounts) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
//this.baseTime=param.getBaseTime(); //this.baseTime=param.getBaseTime();
// WriteScheduleSummary(chromosome); // WriteScheduleSummary(chromosome);
...@@ -1678,8 +1683,8 @@ public class PlanResultService { ...@@ -1678,8 +1683,8 @@ public class PlanResultService {
// 这里需要重新加载场景,因为数据库已经有新订单了 // 这里需要重新加载场景,因为数据库已经有新订单了
// 然后使用类似复制的逻辑,将新订单排在afterOrderId后面 // 然后使用类似复制的逻辑,将新订单排在afterOrderId后面
GlobalParam globalParam = new GlobalParam();
Chromosome chromosome = _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome = _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
// 从数据库加载新插入的订单及其工序 // 从数据库加载新插入的订单及其工序
ProdLaunchOrder newLaunchOrder = _prodLaunchOrderService.lambdaQuery() ProdLaunchOrder newLaunchOrder = _prodLaunchOrderService.lambdaQuery()
...@@ -1717,9 +1722,8 @@ public class PlanResultService { ...@@ -1717,9 +1722,8 @@ public class PlanResultService {
public Chromosome MergeOrder(String SceneId,String sourceorderId,String targetorderId) { public Chromosome MergeOrder(String SceneId,String sourceorderId,String targetorderId) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
//this.baseTime=param.getBaseTime(); //this.baseTime=param.getBaseTime();
// WriteScheduleSummary(chromosome); // WriteScheduleSummary(chromosome);
...@@ -1733,9 +1737,8 @@ public class PlanResultService { ...@@ -1733,9 +1737,8 @@ public class PlanResultService {
public Chromosome AddMaintenanceWindow(String SceneId, Long machineId, MaintenanceWindow maintenanceWindow) { public Chromosome AddMaintenanceWindow(String SceneId, Long machineId, MaintenanceWindow maintenanceWindow) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
...@@ -1750,9 +1753,8 @@ public class PlanResultService { ...@@ -1750,9 +1753,8 @@ public class PlanResultService {
public Chromosome DelMaintenanceWindow(String SceneId, Long machineId,String maintenanceId) { public Chromosome DelMaintenanceWindow(String SceneId, Long machineId,String maintenanceId) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
...@@ -1766,8 +1768,8 @@ public class PlanResultService { ...@@ -1766,8 +1768,8 @@ public class PlanResultService {
} }
public Chromosome DelMaintenanceWindowBatch(String SceneId, Long machineId, List<String> maintenanceIds) { public Chromosome DelMaintenanceWindowBatch(String SceneId, Long machineId, List<String> maintenanceIds) {
GlobalParam globalParam = new GlobalParam();
Chromosome chromosome = _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome = _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
ScheduleOperationService ScheduleOperation = new ScheduleOperationService(materialRequirementService,this); ScheduleOperationService ScheduleOperation = new ScheduleOperationService(materialRequirementService,this);
...@@ -1780,9 +1782,8 @@ public class PlanResultService { ...@@ -1780,9 +1782,8 @@ public class PlanResultService {
public List<MaintenanceWindow> GetMaintenanceWindow(String SceneId, Long machineId, MaintenanceWindow maintenanceWindow) { public List<MaintenanceWindow> GetMaintenanceWindow(String SceneId, Long machineId, MaintenanceWindow maintenanceWindow) {
GlobalParam globalParam=new GlobalParam();
Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId); Chromosome chromosome= _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = buildGlobalParamFromSnapshot(SceneId, chromosome);
...@@ -1850,7 +1851,7 @@ public class PlanResultService { ...@@ -1850,7 +1851,7 @@ public class PlanResultService {
List<ProdEquipment> ProdEquipments= _prodEquipmentService.lambdaQuery() List<ProdEquipment> ProdEquipments= _prodEquipmentService.lambdaQuery()
.eq(ProdEquipment::getSceneId,SceneId) .eq(ProdEquipment::getSceneId,SceneId)
.list(); .list();
GlobalParam globalParam=InitGlobalParam(); GlobalParam globalParam = buildInitialGlobalParam(SceneId, null, null, null);
List<ProdLaunchOrder> ProdLaunchOrders= _prodLaunchOrderService.lambdaQuery() List<ProdLaunchOrder> ProdLaunchOrders= _prodLaunchOrderService.lambdaQuery()
.eq(ProdLaunchOrder::getSceneId,SceneId) .eq(ProdLaunchOrder::getSceneId,SceneId)
.list(); .list();
...@@ -1887,6 +1888,7 @@ public class PlanResultService { ...@@ -1887,6 +1888,7 @@ public class PlanResultService {
chromosomes.setBaseTime(param.getBaseTime()); chromosomes.setBaseTime(param.getBaseTime());
// chromosomes.setOperatRel(new CopyOnWriteArrayList<>(entryRel)); // chromosomes.setOperatRel(new CopyOnWriteArrayList<>(entryRel));
// 保存chromosomes到文件 // 保存chromosomes到文件
saveGlobalParamSnapshot(chromosomes, globalParam);
boolean saved = _sceneService.saveChromosomeToFile(chromosomes, SceneId); boolean saved = _sceneService.saveChromosomeToFile(chromosomes, SceneId);
if (!saved) { if (!saved) {
throw new BusinessException("排产计算结果保存失败,请稍后重试或联系管理员"); throw new BusinessException("排产计算结果保存失败,请稍后重试或联系管理员");
...@@ -1916,7 +1918,6 @@ public class PlanResultService { ...@@ -1916,7 +1918,6 @@ public class PlanResultService {
FileHelper.writeLogFile(String.format("Setup Time: %f minutes", schedule.getTotalChangeoverTime())); FileHelper.writeLogFile(String.format("Setup Time: %f minutes", schedule.getTotalChangeoverTime()));
FileHelper.writeLogFile(String.format("Flow Time: %f minutes", schedule.getTotalFlowTime())); FileHelper.writeLogFile(String.format("Flow Time: %f minutes", schedule.getTotalFlowTime()));
FileHelper.writeLogFile(String.format("Machine Load Balance: %.2f%%", schedule.getMachineLoadStd() * 100)); FileHelper.writeLogFile(String.format("Machine Load Balance: %.2f%%", schedule.getMachineLoadStd() * 100));
FileHelper.writeLogFile(String.format("Semi JIT Slack: %f minutes", schedule.getSemiJitSlack()));
FileHelper.writeLogFile("-------------------------"); FileHelper.writeLogFile("-------------------------");
// 按订单分组写入 // 按订单分组写入
...@@ -2172,6 +2173,47 @@ if(job.getGeneDetails()!=null) ...@@ -2172,6 +2173,47 @@ if(job.getGeneDetails()!=null)
FileHelper.writeLogFile("初始化约束-----------结束-------"); FileHelper.writeLogFile("初始化约束-----------结束-------");
return globalParam; return globalParam;
} }
private GlobalParam buildInitialGlobalParam(String sceneId, Long userId, Long baseRuleId, String userRuleId) {
// 先拿到基础约束参数,再叠加保存的 KPI 配置,形成本次排产实际使用的 GlobalParam。
GlobalParam globalParam = InitGlobalParam();
Object kpiConfig = scheduleStrategyService.loadEffectiveKpiConfig(userId, baseRuleId, sceneId, userRuleId);
globalParam.applyKpiConfig(kpiConfig);
return globalParam;
}
private GlobalParam buildGlobalParamFromSnapshot(Chromosome chromosome) {
return buildGlobalParamFromSnapshot(null, chromosome);
}
private GlobalParam buildGlobalParamFromSnapshot(String sceneId, Chromosome chromosome) {
// 局部排产优先复用染色体里保存的参数快照,避免重新读取数据库或回退到默认值。
if (chromosome != null && chromosome.getGlobalParamSnapshot() != null) {
return chromosome.getGlobalParamSnapshot().copy();
}
// 没有快照时才创建默认参数,并把它补回快照,保证后续局部操作还能复用。
GlobalParam globalParam = new GlobalParam();
if (chromosome != null) {
chromosome.setGlobalParamSnapshot(globalParam.copy());
}
return globalParam;
}
private GlobalParam buildGlobalParamFromSnapshot(Chromosome chromosome, boolean initConstraintFallback) {
return buildGlobalParamFromSnapshot(null, chromosome);
}
private GlobalParam buildGlobalParamFromSnapshot(String sceneId, Chromosome chromosome, boolean initConstraintFallback) {
return buildGlobalParamFromSnapshot(sceneId, chromosome);
}
private void saveGlobalParamSnapshot(Chromosome chromosome, GlobalParam globalParam) {
if (chromosome != null && globalParam != null) {
chromosome.setGlobalParamSnapshot(globalParam.copy());
}
}
private List<Order> InitOrder(List<ProdLaunchOrder> ProdLaunchOrders) private List<Order> InitOrder(List<ProdLaunchOrder> ProdLaunchOrders)
{ {
return InitOrder(ProdLaunchOrders, Collections.emptyList()); return InitOrder(ProdLaunchOrders, Collections.emptyList());
...@@ -3201,7 +3243,10 @@ if(job.getGeneDetails()!=null) ...@@ -3201,7 +3243,10 @@ if(job.getGeneDetails()!=null)
public List<Machine> InitCalendarToAllMachines2(String SceneId) { public List<Machine> InitCalendarToAllMachines2(String SceneId) {
GlobalParam globalParam=InitGlobalParam(); Chromosome chromosome = _sceneService.loadChromosomeFromFile(SceneId);
GlobalParam globalParam = (chromosome != null && chromosome.getGlobalParamSnapshot() != null)
? chromosome.getGlobalParamSnapshot().copy()
: InitGlobalParam();
boolean IsUseCalendar = globalParam.isIsUseCalendar(); boolean IsUseCalendar = globalParam.isIsUseCalendar();
// 按设备分组 // 按设备分组
......
...@@ -14,9 +14,11 @@ import org.springframework.stereotype.Service; ...@@ -14,9 +14,11 @@ import org.springframework.stereotype.Service;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collections; import java.util.Collections;
import java.util.Comparator; import java.util.Comparator;
import java.util.HashMap;
import java.util.HashSet; import java.util.HashSet;
import java.util.List; import java.util.List;
import java.util.Locale; import java.util.Locale;
import java.util.Map;
import java.util.Set; import java.util.Set;
import java.util.stream.Collectors; import java.util.stream.Collectors;
...@@ -65,6 +67,29 @@ public class ScheduleStrategyService { ...@@ -65,6 +67,29 @@ public class ScheduleStrategyService {
} }
} }
public Object loadEffectiveKpiConfig(Long userId, Long baseRuleId, String sceneId, String userRuleId) {
try {
Map<String, Object> params = new HashMap<>();
Long effectiveUserId = resolveScheduleUserId(sceneId, userId);
if (effectiveUserId != null) {
params.put("userId", effectiveUserId);
}
if (baseRuleId != null) {
params.put("baseRuleId", baseRuleId);
}
if (userRuleId != null && !userRuleId.trim().isEmpty()) {
params.put("userRuleId", userRuleId);
}
Map<String, Object> effectiveRule = userStrategyRuleService.getEffectiveRule(params);
return effectiveRule == null ? null : effectiveRule.get("kpiConfig");
} catch (Exception e) {
log.warn("Load KPI strategy failed, use GlobalParam default KPI. sceneId={}, userId={}, baseRuleId={}, userRuleId={}",
sceneId, userId, baseRuleId, userRuleId, e);
return null;
}
}
public OrderSortRule createMultiConditionRule(List<Order> orders) { public OrderSortRule createMultiConditionRule(List<Order> orders) {
return createMultiConditionRule(orders, Collections.emptyList()); return createMultiConditionRule(orders, Collections.emptyList());
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment