排队系统的模拟模拟(simulation)是计算机的一个重要应用,是指用计算机来仿真现实系统的操作并收集统计数据。例如,我们想模拟有K个出纳员的银行操作系统,以确定要提供合理的服务时间,最小的K值是多少。用计算机来模拟有很多优点:首先,不需要真实的顾客就能够得到统计信息;第二,由于计算机速度很快,使用计算机模拟比真实的实现要快很多;第三,模拟结果可以简单地重现。离散事件的模拟一个离散事件模拟器由事件处理组成;一般有两类事件:客户到达服务完毕,客户离开我们可以在模拟过程中统计客户的排队长度、等待时间、服务员的连续工作时间、空闲时间等统计信息。基本方法用概率函数产生客户到达时间以及每个客户所需的服务时间的输入流,按到达时间排序。不需要使用真实的精确时间,只要用一个时间单位即可,我们把这个单位叫做一个嘀嗒(tick)。嘀嗒(tick)是指模拟中的时间单位。时间驱动的模拟在离散的时间驱动模拟(discretetime-drivensimulation)中,模拟开始时时钟是0嘀嗒,随后每一步都把时钟加1嘀嗒,并检查这个时间是否有事件发生;如果有事件发生,我们就处理该事件并生成统计信息;如果输入流中没有一个顾客且出纳员都空闲时,模拟结束。离散的时间驱动模拟(discretetime-drivensimulation)连续地处理每个时间单位;这种模拟对于时间间隔很大的事件很不适合。如何解决这个问题这个模拟策略的问题在于运行时间不依赖于顾客数或者事件数;而是取决于嘀嗒数,试想如果我们把时钟单位改成微滴嗒,并把每次输入中的时间都乘以1,000,000,那样这个模拟将要花费1,000,000倍的执行时间。解决这个问题的关键就是在每一步跳到下一个事件发生的时刻,这就是所谓的事件驱动模拟(event-drivensimulation)。事件驱动的模拟在任何时刻,下一个事件只有两种情况:一种是输入流中下一个顾客的到达或者出纳柜台前某一个顾客的离开。事件发生的时刻都可获知,所以我们只需要找出最先发生的事件并处理该事件(并把当前时间设置成该事件发生的时间)。事件驱动模拟(event-drivensimulation)直接把当前时间跳到下一个事件发生的时刻。如果在连续事件之间的滴嗒间隔很大时,用事件驱动模拟是合适的。要解决的问题作业二。单个服务器的排队系统模拟过程:生成20个事件,存入队列。每个事件包括一个SavingAccount类的对象和该对象的到达时间当前时间设为0依次从队列中取出事件。如果当前时间小于到达时间,将当前时间设为到达时间。生成服务时间,将当前时间加上服务时间作为当前时间。输出处理过程。如何产生事件:事件的产生是一个随机过程。在排队系统中,客户得到达是随机的,服务时间也是随机的。因此,此问题的关键是如何模拟随机过程。如何产生均匀分布的随机值均匀分布可以通过随机数产生器产生。如某个随机过程产生的值服从[a,b]之间的均匀分布,则可以生成一个[a,b]之间的一个随机值,把此随机值作为随机过程产生的值[a,b]之间的随机值:rand()*(b-a+1)/(RAND_MAX+1)几个重要的随机值的生成到达时间间隔:[3,8]之间的随机数服务时间:【2,7】之间的随机数存款金额:【1,50】之间的随机数,将此随机数乘1000存款类型:【0,6】之间的随机数,分别对应六种存款类型totalWaitTime=0;设置顾客开始到达的时间currentTime=0;for(i=0;icustomNum;++i){生成下一顾客到达的间隔时间;下一顾客的到达时间currentTime+=下一顾客到达的间隔时间;生成存款类型、金额、服务完成时间;将下一顾客的到达时间入队;}while(顾客队列非空){取队头顾客;输出顾客信息;}