void patientDeparture() { S_Patient this_Patient = beds[currentEvent.EventType].returnPatient(); if (this_Patient.totalTime > 0.5) { sl3[(int)this_Patient.arriveTime] += 1; } //依靠当前事件的 EventType 参数来确定窗口 //判断实验终止条件,如果已经到达最大服务时间,则不进行处理 if (currentEvent.occur_time < 24) { //如果队列中还有病人,则生成下一位病人的离开事件 if (PatientQueue.Count > 0) { S_Patient patient = PatientQueue[0]; PatientQueue.RemoveAt(0); double InterTime = 0; double waitTime = 0; if (patient.remainTime > 0) {// 曾经被退回来的病人 InterTime = patient.remainTime; waitTime = currentEvent.occur_time - patient.lastLeave; patient.totalTime += waitTime; if (patient.lastLeave < patient.arriveTime + 0.5 && currentEvent.occur_time > patient.arriveTime + 0.5) { sl2[(int)patient.arriveTime - 1] += 1; } } else { // 第一次接受治疗的病人 InterTime = RandExp(miu); //计算当前病人的治疗时间 waitTime = currentEvent.occur_time - patient.arriveTime; patient.totalTime += waitTime; if (waitTime > 0.5) { sl1[(int)patient.arriveTime] += 1; sl2[(int)patient.arriveTime] += 1; } } double time = currentEvent.occur_time + InterTime; //计算下一位病人离开事件的发生时间 S_Event temp_event = new S_Event(time, currentEvent.EventType); addEvent(events, temp_event); beds[currentEvent.EventType].servePatient(patient, temp_event); //从队列中取出下一位病人并分配至当前床位 } else { beds[currentEvent.EventType].setIdle(); } } }
void patientArrive(int currentHour) { patientCount[currentHour] += 1; //该时间段内病人总数+1 //-------------------------------生成下一名病人的到达事件---------------------------------------// double intertime = RandExp((double)lambda[currentHour]); //下一名救护车病人到达的时间间隔 double time = currentEvent.occur_time + intertime; //下一名救护车病人的到达时间 S_Event temp_event = new S_Event(time, -1); //生成下一名病人的到达事件 //判断实验终止条件,如果已经到达24点,则不将事件加入事件列表。 if (time < 24) { addEvent(events, temp_event); } //------------------------------根据到达事件生成当前病人----------------------------------------// S_Patient inPatient = new S_Patient(currentEvent.occur_time); //将病人加入排队 PatientQueue.Add(inPatient); //--------------------------------处理目前队列中的病人-----------------------------------------// int idleIndex = GetIdleBed(); //寻找空闲的床位 if (idleIndex >= 0) { S_Patient outPatient = PatientQueue[0]; time = currentEvent.occur_time + RandExp(miu); PatientQueue.RemoveAt(0); //将病人从队列中取出 beds[idleIndex].setBusy(); //将床位状态设置为“繁忙” temp_event = new S_Event(time, idleIndex); //产生对应的离开事件 addEvent(events, temp_event); beds[idleIndex].servePatient(outPatient, temp_event); //将病人安排至床位 } else { //计算队长的变化 } }
void bedsSwitch(int amount) { if (amount > 0) //增加床位 { for (int i = 0; i != amount; i++) { beds.Add(new S_Beds()); } } else if (amount < 0) { //减少床位 Random rand = new Random(); for (int i = 0; i != (-amount); i++) { int r = rand.Next(0, beds.Count - 1); //处理标记为r处的床位的病人 //首先检查这个床位是否有人,如果没有的话就跳过 if (beds[r].isIdle()) { beds.RemoveAt(r); } else { //计算病人剩余的治疗时间 int idleNum = GetIdleBed(); double currentTime = currentEvent.occur_time; double endTime = beds[r].LeaveEvent.occur_time; S_Patient rePatient = beds[r].returnPatient(); rePatient.remainTime = endTime - currentTime; //移除病人原本的离开事件 events.Remove(beds[r].LeaveEvent); //根据选择的策略处理换班 switch (switchRule) { case 0: if (idleNum != -1) { //若存在空闲服务台,正在服务中的服务台将工作转交给空闲服务台后下班 S_Event event_0 = new S_Event(endTime, idleNum); addEvent(events, event_0); beds[idleNum].servePatient(rePatient, event_0); } else { //否则,正在服务中的服务台将完成当前顾客的服务后下班 if (rePatient.totalTime > 0.5) { sl3[(int)rePatient.arriveTime] += 1; } } break; case 1: //正在服务中的服务台将直接下班,其正在服务中的顾客被退回队首 rePatient.lastLeave = currentTime; PatientQueue.Insert(0, rePatient); break; case 2: //正在服务中的服务台完成当前顾客的服务后下班 if (rePatient.totalTime > 0.5) { sl3[(int)rePatient.arriveTime] += 1; } break; } beds.RemoveAt(r); } for (int j = 0; j != events.Count; j++) { if (events[j].EventType >= r) { events[j].EventType -= 1; } } } } for (int j = 0; j != events.Count; j++) { if (events[j].EventType == -1) { S_Event newEvent = events[j]; newEvent.occur_time = currentEvent.occur_time; events.RemoveAt(j); addEvent(events, newEvent); break; } } }
public void servePatient(S_Patient patient, S_Event @event) { this.patient = patient; this.LeaveEvent = @event; }