如何从Service Block获取Busy/Idle状态?用于Gantt Chart开发
获取Service Block状态的方法及甘特图实现示例
核心方法:直接获取Service Block状态
AnyLogic的ServiceBlock组件自带getState()方法,调用后会返回ServiceBlock.State枚举类型,包含你需要的核心状态:
IDLE:空闲BUSY:正在处理实体PREEMPTED:被抢占BLOCKED:阻塞FAILED:故障
代码示例:记录状态变化用于甘特图
1. 定义状态日志数据结构
先创建自定义数据类型MachineLog,用来存储状态变化的时间节点、机器标识和状态:
public class MachineLog { public double startTime; public double endTime; public String machineName; public ServiceBlock.State state; public MachineLog(double startTime, String machineName, ServiceBlock.State state) { this.startTime = startTime; this.machineName = machineName; this.state = state; } }
在主代理中创建列表存储日志:
ArrayList<MachineLog> machineStateLogs = new ArrayList<>(); MachineLog currentActiveLog;
2. 在Service Block事件中记录状态切换
选中目标Service Block,在对应事件中添加代码,记录状态变化:
- On seize(开始处理实体):
// 结束上一条未闭合的日志(如果有) if(currentActiveLog != null) { currentActiveLog.endTime = time(); } // 记录BUSY状态开始 currentActiveLog = new MachineLog(time(), this.getName(), ServiceBlock.State.BUSY); machineStateLogs.add(currentActiveLog);
- On release(完成实体处理):
// 闭合BUSY状态日志 currentActiveLog.endTime = time(); // 记录IDLE状态开始 currentActiveLog = new MachineLog(time(), this.getName(), ServiceBlock.State.IDLE); machineStateLogs.add(currentActiveLog);
如果需要处理故障场景,在On failure和On repair complete事件中添加类似逻辑:
// On failure事件 currentActiveLog.endTime = time(); currentActiveLog = new MachineLog(time(), this.getName(), ServiceBlock.State.FAILED); machineStateLogs.add(currentActiveLog); // On repair complete事件 currentActiveLog.endTime = time(); currentActiveLog = new MachineLog(time(), this.getName(), ServiceBlock.State.IDLE); machineStateLogs.add(currentActiveLog);
3. 将日志数据导入甘特图
遍历日志列表,将状态段数据传递给甘特图组件(假设你的甘特图组件名为ganttChart):
for(MachineLog log : machineStateLogs) { // 跳过未结束的状态记录 if(log.endTime <= 0) continue; ganttChart.addTask( log.machineName, // 机器名称作为任务名称 log.startTime, // 状态开始时间 log.endTime - log.startTime, // 状态持续时长 log.state.toString() // 状态标签(显示在甘特图上) ); }
如果需要实时更新甘特图,可在每次状态记录后调用ganttChart.refresh()。
注意事项
- 若Service Block启用了抢占、延迟或故障逻辑,必须对应添加状态切换的日志记录,避免数据缺失。
- 多机器场景下,可通过循环遍历所有Service Block实例,统一绑定事件逻辑。
内容的提问来源于stack exchange,提问作者Mo1409
相关产品推荐
相关产品推荐

