package com.chinaztt.mes.aps.core.domain;
|
|
import com.chinaztt.mes.aps.core.helper.Constants;
|
import com.chinaztt.mes.aps.core.solver.StartTimeUpdatingVariableListener;
|
import com.chinaztt.mes.aps.core.solver.TaskDifficultyComparator;
|
import com.chinaztt.mes.aps.entity.ResourceDuration;
|
import com.fasterxml.jackson.annotation.JsonIgnore;
|
import lombok.Data;
|
import org.optaplanner.core.api.domain.entity.PlanningEntity;
|
import org.optaplanner.core.api.domain.variable.*;
|
|
import java.math.BigDecimal;
|
import java.time.LocalDateTime;
|
import java.util.Optional;
|
import java.util.Set;
|
|
/**
|
* @Author: zhangxy
|
* @Date: 2020-10-19 19:42
|
*/
|
@PlanningEntity(difficultyComparatorClass = TaskDifficultyComparator.class)
|
@Data
|
public class Task extends AbstractTaskOrResource {
|
|
/**
|
* id 可能为空
|
*/
|
private Long id;
|
|
private Long orderId;
|
|
private Long routingId;
|
|
private Long routingOperationId;
|
|
private int orderPriority;
|
|
private int operationPriority;
|
|
private String opNo;
|
|
private String name;
|
|
private BigDecimal quantity;
|
|
private Long partId;
|
|
private Set<Long> capabilityIds;
|
|
@JsonIgnore
|
private Task successorOfRouting;
|
|
@JsonIgnore
|
private Task predecessorOfRouting;
|
|
|
@CustomShadowVariable(variableListenerClass = StartTimeUpdatingVariableListener.class,
|
sources = {@PlanningVariableReference(variableName = "previousTaskOrResource"),})
|
private LocalDateTime planStartTime;
|
|
@JsonIgnore
|
@PlanningVariable(valueRangeProviderRefs = {"resourceRange", "taskRange"},
|
graphType = PlanningVariableGraphType.CHAINED)
|
private AbstractTaskOrResource previousTaskOrResource;
|
|
|
@AnchorShadowVariable(sourceVariableName = "previousTaskOrResource")
|
private ResourceBo resourceBo;
|
|
|
|
@Override
|
public LocalDateTime getPlanEndTime() {
|
if (this.planStartTime == null || this.getResourceBo() == null || this.getResourceBo().getDurations() == null) {
|
return LocalDateTime.now();
|
}
|
Optional<ResourceDuration> opt = this.getResourceBo().getDurations().stream().filter(d -> d.getPartId().equals(this.getPartId())).findFirst();
|
if (opt.isPresent()) {
|
return this.planStartTime.plusMinutes(calculateCostTime(quantity, opt.get()));
|
}
|
return this.planStartTime;
|
}
|
|
|
/**
|
* 计算task耗用时间,单位分钟
|
* @param quantity
|
* @param rd
|
* @return
|
*/
|
private long calculateCostTime(BigDecimal quantity, ResourceDuration rd) {
|
long cost = 0L;
|
if (Constants.UNIT_PER_MIN.equals(rd.getProductionRateUnit())) {
|
//单位数/分钟
|
cost += rd.getSetupTime().longValue();
|
cost += quantity.divide(rd.getProductionRate(), 0, BigDecimal.ROUND_UP).longValue();
|
cost += rd.getPostProcessing().longValue();
|
} else if (Constants.MIN_PER_UNIT.equals(rd.getProductionRateUnit())) {
|
//分钟数/单位
|
cost += rd.getSetupTime().longValue();
|
cost += quantity.multiply(rd.getProductionRate()).intValue();
|
cost += rd.getPostProcessing().longValue();
|
}
|
return cost;
|
}
|
|
@Override
|
public boolean equals(Object o) {
|
if (this == o) {
|
return true;
|
}
|
if (o == null || getClass() != o.getClass()) {
|
return false;
|
}
|
|
Task task = (Task) o;
|
|
if (orderPriority != task.orderPriority) {
|
return false;
|
}
|
if (operationPriority != task.operationPriority) {
|
return false;
|
}
|
if (!orderId.equals(task.orderId)) {
|
return false;
|
}
|
if (!routingOperationId.equals(task.routingOperationId)) {
|
return false;
|
}
|
if (!quantity.equals(task.quantity)) {
|
return false;
|
}
|
return partId.equals(task.partId);
|
}
|
|
@Override
|
public int hashCode() {
|
int result = orderId.hashCode();
|
result = 31 * result + routingOperationId.hashCode();
|
result = 31 * result + orderPriority;
|
result = 31 * result + operationPriority;
|
result = 31 * result + quantity.hashCode();
|
result = 31 * result + partId.hashCode();
|
return result;
|
}
|
|
@Override
|
public String toString() {
|
return "Task{" +
|
"operationPriority=" + operationPriority +
|
", name='" + name + '\'' +
|
", quantity=" + quantity +
|
", capabilityIds=" + capabilityIds +
|
", planStartTime=" + planStartTime +
|
'}';
|
}
|
}
|