Error handling Anylogic-内部错误:引擎仍计划了x个事件:xyz:[null]

Error handling Anylogic-内部错误:引擎仍计划了x个事件:xyz:[null],error-handling,runtimeexception,anylogic,Error Handling,Runtimeexception,Anylogic,停止模拟后,我偶尔会收到以下错误消息: 例如: Exception during stopping the engine: INTERNAL ERROR(S): Engine still has 6 events scheduled: 2386.0: [null] java.lang.RuntimeException: INTERNAL ERROR(S): Engine still has 6 events scheduled: 2386.0: [null] at com.anylogi

停止模拟后,我偶尔会收到以下错误消息:

例如:

Exception during stopping the engine:
INTERNAL ERROR(S):
Engine still has 6 events scheduled: 2386.0:  [null]

java.lang.RuntimeException: INTERNAL ERROR(S):
Engine still has 6 events scheduled: 2386.0:  [null]

at com.anylogic.engine.Engine.g(Unknown Source)
at com.anylogic.engine.Engine.stop(Unknown Source)
at com.anylogic.engine.ExperimentSimulation.stop(Unknown Source)
at com.anylogic.engine.gui.ExperimentHost.executeCommand(Unknown Source)
at com.anylogic.engine.internal.webserver.l.onCommand(Unknown Source)
...
我的模拟模型如下所示:

该模型是对作业车间调度问题的模拟,并执行以下操作:

  • 通过源代码块中的
    inject(20)
    生成作业代理
  • 作业进入数据库定义的机器,并在等待块中等待
  • 作业由其他代理从等待块中释放
  • 作业在服务块中处理
  • 这些作业将此过程再重复4次
  • 步骤3中总共有5个代理—我们称它们为调度代理—它们使用
    Wait.free()
    方法将代理设置为自由。一个代理控制一个等待块。所有5个调度代理同时工作,并通过
    Main
    代理进行同步(
    Main
    通知调度代理)。模拟启动后,立即解锁保持块。它们的存在也是为了同步。每个调度代理都拥有自己的线程,该线程通过
    Thread.start()
    Main
    中定义的超时事件(发生一次,时间=0)启动

    来自调度代理的线程如下所示:

    new Thread(new Runnable() {
        public void run() {
            synchronized (sync_obj) {
                sync_obj.waituntilJobarrives();
                sync_obj.Waitblock.free(a_Job);
                synv_obj.waituntilJobisfinished();
                repeat();
            }
        }
    });
    
    现在我的问题是:当我开始模拟时,作业正常生成并移动到分配的等待块。之后,调度代理开始工作并释放作业,但有时调度代理调用
    Waitblock.free()
    方法,作业未设置为自由(调用方法时使用
    traceln()
    进行检查)。为了仔细检查这个问题,我实现了按钮,手动调用
    Waitblock.free()
    方法,但是作业代理仍然不会离开等待块。如果作业未被代理释放,则作业车间的模拟将停留在那里。模拟将继续运行,但这20个作业从未完成,并且不会显示任何错误消息(技术上没有错误)。只有在停止模拟后,上面显示的错误消息才会出现在控制台中

    更糟糕的是,这个错误并非总是出现。有时模拟工作正常,有时等待块停止反应。通常,在模拟足够长的时间后,会出现此错误,并且一个或多个等待块停止反应

    我从阅读错误消息中猜测,引擎收到了将代理从等待块中释放的命令。它现在就是做不到。我如何或可以控制引擎计划的事件顺序(个人学习版)?还是有其他解决问题的方法

    我非常感谢你的帮助

    编辑:通过删除
    保持块
    引擎的错误仍然安排了X个事件
    并不经常出现。但是“Wait Block”仍然不响应
    Waitblock.free()
    方法,并且控制台中出现以下错误消息:

    java.lang.RuntimeException: root.w_Warteblock1.readyEntities.output.readyNotificationAsync.event: negative timeout: -1.25
        at com.anylogic.engine.Engine.error(Unknown Source)
        at com.anylogic.engine.EventOriginator.g(Unknown Source)
        at com.anylogic.engine.EventOriginator.c(Unknown Source)
        at com.anylogic.engine.EventTimeout.restart(Unknown Source)
        at com.anylogic.libraries.processmodeling.AsynchronousExecutor_xjal.a(Unknown Source)
        at com.anylogic.libraries.processmodeling.OutputBlock.notifyReady(Unknown Source)
        at com.anylogic.libraries.processmodeling.OutputBuffer.a(Unknown Source)
        at com.anylogic.libraries.processmodeling.OutputBuffer.take(Unknown Source)
        at com.anylogic.libraries.processmodeling.Wait.free(Unknown Source)
    

    这看起来更像是一个常见错误,我可以捕捉到。因此,我当前的解决方法是在调用
    Waitblock.free()
    方法的线程周围使用try-and-catch块,并使用保存在excel文件中的模拟进度重新启动模拟。

    我将告诉您我的想法,但这些信息可能不足以得出结论:

    我记得当我暂停模拟,然后删除代理,然后停止模拟时,会出现此错误。如果我遵循这些步骤,我会得到那个错误

    这意味着当您停止模拟时,您需要给模拟至少一毫秒的时间才能完成计划的事件。。。在这种情况下,计划的事件位于线程上。因此,解决方案是在单击“停止”按钮之前使用finishSimulation()停止模拟。您必须在finishSimulation()函数运行之前终止线程。。。我对此不确定,但试试看


    这是第一个问题。。。我认为第二个问题与等待后的等待有关。请注意,如果您的保持块被阻止,并且您尝试从等待块释放多个代理。。。取消阻止保留时,仅释放1个代理。这是因为在等待块的出口处只有一个代理的空间。。。如果你犯了这个错误,代理将永远处于等待状态。。解决方案是在等待块之后使用队列。我不认为这个问题与你所犯的错误有关…

    我会告诉你我的想法,但这些信息可能不足以得出结论:

    我记得当我暂停模拟,然后删除代理,然后停止模拟时,会出现此错误。如果我遵循这些步骤,我会得到那个错误

    这意味着当您停止模拟时,您需要给模拟至少一毫秒的时间才能完成计划的事件。。。在这种情况下,计划的事件位于线程上。因此,解决方案是在单击“停止”按钮之前使用finishSimulation()停止模拟。您必须在finishSimulation()函数运行之前终止线程。。。我对此不确定,但试试看


    这是第一个问题。。。我认为第二个问题与等待后的等待有关。请注意,如果您的保持块被阻止,并且您尝试从等待块释放多个代理。。。取消阻止保留时,仅释放1个代理。这是因为在等待块的出口处只有一个代理的空间。。。如果你犯了这个错误,代理将永远处于等待状态。。解决方案是在等待块之后使用队列。我不认为这个问题与您遇到的错误有关…

    我在测试套件中遇到了这个问题。我打电话给:

    engine.finish();
    
    而不是:

    engine.stop();