Commit 08991d0b authored by Tong Li's avatar Tong Li

设备日历生成太多

parent c7e03b35
......@@ -68,7 +68,7 @@ public class Initialization {
int gsCount = (int) (param.getPopulationSize() * param.getGsRatio());
int lsCount =gsCount+ (int) (param.getPopulationSize() * param.getLsRatio());
int rsCount = param.getPopulationSize() - gsCount - lsCount;
int populationSize=param.getPopulationSize();
int populationSize=param.getPopulationSize();
// 并行循环:对应 Parallel.For(0, PopulationSize, i => { ... })
IntStream.range(0, populationSize)
.parallel() // 开启并行
......@@ -76,7 +76,7 @@ int populationSize=param.getPopulationSize();
Chromosome chromo = new Chromosome(); // 初始化染色体
// chromo.setObjectiveWeights(_objectiveWeights);
// chromo.setInitMachines(ProductionDeepCopyUtil.deepCopyList(machines));
chromo.setOrders(new CopyOnWriteArrayList<>(orders));
chromo.setOrders(new CopyOnWriteArrayList<>(orders));
// 全局选择(GS):按GlobalOpId顺序生成MachineSelection
if (i < gsCount) {
chromo.setGsOrls(1);
......@@ -347,13 +347,16 @@ chromo.setOrders(new CopyOnWriteArrayList<>(orders));
List<Chromosome> population = new ArrayList<>();
int populationSize = param.getPopulationSize();
this.baseTime=param.getBaseTime();
// 按比例生成不同启发式规则的个体
int sptCount = (int) (populationSize * 0.2);
int lptCount = sptCount + (int) (populationSize * 0.1);
int eddCount = lptCount + (int) (populationSize * 0.2);
int crCount = eddCount + (int) (populationSize * 0.2);
int sstCount = crCount + (int) (populationSize * 0.2);
int lsCount = populationSize - sstCount;
// 按比例生成不同启发式规则的个体(优化:增加混合策略和瓶颈优先)
int sptCount = (int) (populationSize * 0.15);
int eddsptCount = sptCount + (int) (populationSize * 0.15);
int eddCount = eddsptCount + (int) (populationSize * 0.15);
int bottleneckCount = eddCount + (int) (populationSize * 0.15);
int sstCount = bottleneckCount + (int) (populationSize * 0.15);
int crCount = sstCount + (int) (populationSize * 0.1);
int lptCount = crCount + (int) (populationSize * 0.1);
int lsCount = populationSize - lptCount;
IntStream.range(0, populationSize)
.parallel()
.forEach(i -> {
......@@ -364,23 +367,31 @@ chromo.setOrders(new CopyOnWriteArrayList<>(orders));
// SPT规则
chromo.setGenerateType("SPT");
generateChromosomeByType(chromo, 1);
} else if (i < lptCount) {
// LPT规则
chromo.setGenerateType("LPT");
generateChromosomeByType(chromo, 2);
} else if (i < eddsptCount) {
// EDD+SPT混合策略
chromo.setGenerateType("EDD+SPT");
generateEDDSPTChromosome(chromo);
} else if (i < eddCount) {
// EDD规则
chromo.setGenerateType("EDD");
generateChromosomeByType(chromo, 3);
} else if (i < bottleneckCount) {
// 瓶颈优先策略
chromo.setGenerateType("BottleneckFirst");
generateBottleneckFirstChromosome(chromo);
} else if (i < sstCount) {
// SST规则(已有物料排序)
chromo.setGenerateType("SST");
generateSSTChromosome(chromo);
} else if (i < crCount) {
// CR规则
chromo.setGenerateType("CR");
generateCRChromosome(chromo);
} else if (i < sstCount) {
// SST规则
chromo.setGenerateType("SST");
generateSSTChromosome(chromo);
}else {
} else if (i < lptCount) {
// LPT规则
chromo.setGenerateType("LPT");
generateChromosomeByType(chromo, 2);
} else {
// 随机规则
chromo.setGenerateType("LS");
generateLsChromosome(chromo);
......@@ -425,6 +436,7 @@ chromo.setOrders(new CopyOnWriteArrayList<>(orders));
if (considerSequence) {
sortedOps.sort(Comparator.comparing((Entry op) -> op.getPriority())
.thenComparing(Entry::getSequence)
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "") // 相同物料排在一起,减少换型
.thenComparing(op -> {
if (op.getMachineOptions() == null || op.getMachineOptions().isEmpty()) {
return sortType == 1 ? 0.0 : Double.MAX_VALUE; // 空值默认排最前/最后
......@@ -436,7 +448,7 @@ chromo.setOrders(new CopyOnWriteArrayList<>(orders));
}
else{
sortedOps.sort(Comparator.comparing((Entry op) -> op.getPriority())
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "") // 相同物料排在一起,减少换型
.thenComparing(op -> {
if (op.getMachineOptions() == null || op.getMachineOptions().isEmpty()) {
return sortType == 1 ? 0.0 : Double.MAX_VALUE; // 空值默认排最前/最后
......@@ -451,12 +463,13 @@ chromo.setOrders(new CopyOnWriteArrayList<>(orders));
if (considerSequence) {
sortedOps.sort(Comparator.comparing((Entry op) -> op.getPriority())
.thenComparing(Entry::getSequence)
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "") // 相同物料排在一起,减少换型
.thenComparing(op -> dueDateMap.get(op.getGroupId()),
Comparator.nullsLast(Comparator.naturalOrder()))
.thenComparing(randomIds::get));
}else {
sortedOps.sort(Comparator.comparing((Entry op) -> op.getPriority())
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "") // 相同物料排在一起,减少换型
.thenComparing(op -> dueDateMap.get(op.getGroupId()),
Comparator.nullsLast(Comparator.naturalOrder()))
.thenComparing(randomIds::get));
......@@ -551,6 +564,7 @@ chromo.setOrders(new CopyOnWriteArrayList<>(orders));
if (considerSequence) {
sortedOps.sort(Comparator.comparing((Entry op) -> -op.getPriority())
.thenComparing(Entry::getSequence)
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "") // 相同物料排在一起,减少换型
.thenComparing(op -> {
Order order = orderMap.get(op.getGroupId());
return calculateCriticalRatio(order, remainingProcessingTime.getOrDefault(op.getGroupId(), 0.0));
......@@ -558,7 +572,7 @@ chromo.setOrders(new CopyOnWriteArrayList<>(orders));
.thenComparing(randomIds::get));
}else {
sortedOps.sort(Comparator.comparing((Entry op) -> -op.getPriority())
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "") // 相同物料排在一起,减少换型
.thenComparing(op -> {
Order order = orderMap.get(op.getGroupId());
return calculateCriticalRatio(order, remainingProcessingTime.getOrDefault(op.getGroupId(), 0.0));
......@@ -747,6 +761,189 @@ chromo.setOrders(new CopyOnWriteArrayList<>(orders));
return loadCost + processingCost + setupCost;
}
/**
* EDD+SPT混合策略:先按截止日期,再按加工时间
*/
private Chromosome generateEDDSPTChromosome(Chromosome chromosome) {
List<Integer> ms = new ArrayList<>();
List<Integer> os = new ArrayList<>();
Map<Long, Double> machineLoad = new HashMap<>();
Random rnd = new Random();
List<GlobalOperationInfo> globalOpList = new ArrayList<>();
Map<Integer, LocalDateTime> dueDateMap = new HashMap<>();
for (Order order : orders) {
dueDateMap.put(order.getId(), order.getDueDate());
}
Map<Entry, Integer> randomIds = new HashMap<>();
List<Integer> indices = new ArrayList<>();
for (int i = 0; i < allOperations.size(); i++) {
indices.add(i);
}
Collections.shuffle(indices, rnd);
for (int i = 0; i < allOperations.size(); i++) {
randomIds.put(allOperations.get(i), indices.get(i));
}
List<Entry> sortedOps = new ArrayList<>(allOperations);
boolean considerSequence = rnd.nextBoolean();
if (considerSequence) {
sortedOps.sort(Comparator.comparing((Entry op) -> op.getPriority())
.thenComparing(Entry::getSequence)
.thenComparing(op -> dueDateMap.get(op.getGroupId()),
Comparator.nullsLast(Comparator.naturalOrder()))
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "")
.thenComparing(op -> {
if (op.getMachineOptions() == null || op.getMachineOptions().isEmpty()) {
return 0.0;
}
return op.getMachineOptions().get(0).getProcessingTime() * op.getQuantity();
})
.thenComparing(randomIds::get));
} else {
sortedOps.sort(Comparator.comparing((Entry op) -> op.getPriority())
.thenComparing(op -> dueDateMap.get(op.getGroupId()),
Comparator.nullsLast(Comparator.naturalOrder()))
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "")
.thenComparing(op -> {
if (op.getMachineOptions() == null || op.getMachineOptions().isEmpty()) {
return 0.0;
}
return op.getMachineOptions().get(0).getProcessingTime() * op.getQuantity();
})
.thenComparing(randomIds::get));
}
int globalOpId = 0;
for (Entry op : sortedOps) {
int groupId = op.getGroupId();
List<MachineOption> optionalMachines = op.getMachineOptions();
double minLoad = optionalMachines.stream()
.mapToDouble(m -> machineLoad.getOrDefault(m.getMachineId(), 0.0) + m.getProcessingTime())
.min()
.orElse(Double.MAX_VALUE);
List<MachineOption> minLoadMachines = optionalMachines.stream()
.filter(m -> machineLoad.getOrDefault(m.getMachineId(), 0.0) + m.getProcessingTime() == minLoad)
.collect(Collectors.toList());
MachineOption selectedMachine = minLoadMachines.get(rnd.nextInt(minLoadMachines.size()));
OptionalInt index = IntStream.range(0, optionalMachines.size())
.filter(i -> selectedMachine.getMachineId() == optionalMachines.get(i).getMachineId())
.findFirst();
int machineSeq = index.orElse(0) + 1;
ms.add(machineSeq);
machineLoad.put(selectedMachine.getMachineId(),
machineLoad.getOrDefault(selectedMachine.getMachineId(), 0.0) + selectedMachine.getProcessingTime());
os.add(groupId);
GlobalOperationInfo info = new GlobalOperationInfo();
info.setGlobalOpId(globalOpId);
info.setGroupId(op.getGroupId());
info.setSequence(op.getSequence());
info.setOp(op);
globalOpList.add(info);
globalOpId++;
}
chromosome.setGlobalOpList(globalOpList);
chromosome.setOperationSequencing(os);
chromosome.setMachineSelection(ms);
return chromosome;
}
/**
* 瓶颈优先策略:优先安排预计为瓶颈的设备上的工序
*/
private Chromosome generateBottleneckFirstChromosome(Chromosome chromosome) {
List<Integer> ms = new ArrayList<>();
List<Integer> os = new ArrayList<>();
Map<Long, Double> machineLoad = new HashMap<>();
Random rnd = new Random();
List<GlobalOperationInfo> globalOpList = new ArrayList<>();
Map<Entry, Integer> randomIds = new HashMap<>();
List<Integer> indices = new ArrayList<>();
for (int i = 0; i < allOperations.size(); i++) {
indices.add(i);
}
Collections.shuffle(indices, rnd);
for (int i = 0; i < allOperations.size(); i++) {
randomIds.put(allOperations.get(i), indices.get(i));
}
List<Entry> sortedOps = new ArrayList<>(allOperations);
Map<Long, Integer> machineOperationCount = new HashMap<>();
Map<Long, Double> machineTotalTime = new HashMap<>();
for (Entry op : allOperations) {
if (op.getMachineOptions() != null && !op.getMachineOptions().isEmpty()) {
for (MachineOption mo : op.getMachineOptions()) {
machineOperationCount.put(mo.getMachineId(),
machineOperationCount.getOrDefault(mo.getMachineId(), 0) + 1);
machineTotalTime.put(mo.getMachineId(),
machineTotalTime.getOrDefault(mo.getMachineId(), 0.0)
+ mo.getProcessingTime() * op.getQuantity());
}
}
}
sortedOps.sort(Comparator.comparing((Entry op) -> -op.getPriority())
.thenComparing((Entry op) -> {
if (op.getMachineOptions() == null || op.getMachineOptions().isEmpty()) {
return 0.0;
}
double maxTime = 0;
for (MachineOption mo : op.getMachineOptions()) {
double time = machineTotalTime.getOrDefault(mo.getMachineId(), 0.0);
if (time > maxTime) maxTime = time;
}
return -maxTime;
})
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "")
.thenComparing(randomIds::get));
int globalOpId = 0;
for (Entry op : sortedOps) {
int groupId = op.getGroupId();
List<MachineOption> optionalMachines = op.getMachineOptions();
double minLoad = optionalMachines.stream()
.mapToDouble(m -> machineLoad.getOrDefault(m.getMachineId(), 0.0) + m.getProcessingTime())
.min()
.orElse(Double.MAX_VALUE);
List<MachineOption> minLoadMachines = optionalMachines.stream()
.filter(m -> machineLoad.getOrDefault(m.getMachineId(), 0.0) + m.getProcessingTime() == minLoad)
.collect(Collectors.toList());
MachineOption selectedMachine = minLoadMachines.get(rnd.nextInt(minLoadMachines.size()));
OptionalInt index = IntStream.range(0, optionalMachines.size())
.filter(i -> selectedMachine.getMachineId() == optionalMachines.get(i).getMachineId())
.findFirst();
int machineSeq = index.orElse(0) + 1;
ms.add(machineSeq);
machineLoad.put(selectedMachine.getMachineId(),
machineLoad.getOrDefault(selectedMachine.getMachineId(), 0.0) + selectedMachine.getProcessingTime());
os.add(groupId);
GlobalOperationInfo info = new GlobalOperationInfo();
info.setGlobalOpId(globalOpId);
info.setGroupId(op.getGroupId());
info.setSequence(op.getSequence());
info.setOp(op);
globalOpList.add(info);
globalOpId++;
}
chromosome.setGlobalOpList(globalOpList);
chromosome.setOperationSequencing(os);
chromosome.setMachineSelection(ms);
return chromosome;
}
/**
* 随机
*/
......@@ -768,6 +965,7 @@ chromo.setOrders(new CopyOnWriteArrayList<>(orders));
randomIds.put(allOperations.get(i), indices.get(i));
}
sortedOps.sort(Comparator.comparing((Entry op) -> -op.getPriority())
.thenComparing(op -> op.getProductId() != null ? op.getProductId() : "") // 相同物料排在一起,减少换型
.thenComparing(randomIds::get));
......
......@@ -206,7 +206,7 @@ public class PlanResultService {
if(machineIds.get(machineId)!=null&&machineIds.get(machineId)>3600*24*200) {
int day = (int) (machineIds.get(machineId) / 3600 / 24)+100;
day=Math.min(day,400);
// day=Math.min(day,400);
List<TimeSegment> segments = machineScheduler.generateTimeSegment(machine, null, day);
machineScheduler.addSegmentsWithDeduplication(machine, segments);
}
......
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