See:


<project-file type=“source”/>

<content> #include “simagent.h” #include “simprocess.h”

#include <iostream> #define DEBUG SimAgent::SimAgent(SimID id) : SimSchedule(SIM_INFINITY) { ID=id; } SimAgent::~SimAgent() { if (Owner != NULL) Owner→removeAgent(this); size_t n = Agents.size(); if (n > 0) { size_t i = n - 1; while (true) { SimAgent *a=Agents[i]; removeAgent(a); delete a; if (i == 0) break; i–; } } for (std::list<SimAgentManager*>::iterator i = Managers.begin(); i != Managers.end(); i++) delete *i; clear(); } void SimAgent::addManager(SimAgentManager *manager) { if (manager == NULL) return; std::list<SimAgentManager*>::iterator i; for (i = Managers.begin(); i != Managers.end() && (*i) != manager; i++); if (i == Managers.end()) Managers.push_back(manager); int n=Agents.size(); for (int i=0; i<n; i++) manager→addAgent(agent(i)); manager→setOwner(this); } void SimAgent::removeManager(SimAgentManager *manager) { if (manager == NULL) return; std::list<SimAgentManager*>::iterator i; for (i = Managers.begin(); i != Managers.end() && (*i) != manager; i++); if (i != Managers.end()) Managers.erase(i); manager→setOwner(NULL); int n=Agents.size(); for (int i=0; i<n; i++) manager→removeAgent(agent(i)); } void SimAgent::addAgent(SimAgent *agent) { if (agent == NULL || agent→Owner != NULL) return; agent→Index = Agents.size(); Agents.push_back(agent); schedule(agent); for (std::list<SimAgentManager*>::iterator i = Managers.begin(); i != Managers.end(); i++) (*i)→addAgent(agent); } void SimAgent::removeAgent(SimAgent *agent) { int n; n=Agents.size(); if (agent == NULL || agent→Owner != this) return; unschedule(agent); SimAgent *last = Agents.back(); Agents[agent→Index] = last; last→Index = agent→Index; Agents.pop_back(); for (std::list<SimAgentManager*>::iterator i = Managers.begin(); i != Managers.end(); i++) { (*i)→removeAgent(agent); (*i)→agentChangedIndex(Agents.size(), agent→Index); } } void SimAgent::die(SimProcess *proc) { if (Owner != NULL) Owner→removeAgent(this); if (proc != NULL) proc→unregisterAgent(this); } void SimAgent::schedule(SimSchedule *e) { if nothing to add, do nothing

  if (e == NULL) return;
  float Time = e->eventTime();
  if (e->Owner != NULL && (e->Owner != this || 
  		e->EventIndex != Events.end()))
      e->Owner->unschedule(e);
  if (e->Owner == NULL) e->Owner = this;
  if (isInfinity(Time)) {
      e->EventIndex = Events.end();
      return;
  }
  e->EventIndex = Events.insert(std::pair<float, SimSchedule*>(Time, e));
  setEventTime(Events.begin()->second->eventTime());

}

void SimAgent::unschedule(SimSchedule *e) {

  // if nothing to unschedule, do nothing
  if (e == NULL || e->Owner == NULL || e->Owner != this)
      return;
  e->Owner = NULL;
  // if e is not in the event list, no need to remove it from the list
  if (e->EventIndex == Events.end()) return;
  Events.erase(e->EventIndex);
  e->EventIndex = Events.end();
  if (Events.empty()) setEventTime(SIM_INFINITY);
  else setEventTime(Events.begin()->second->eventTime());

}

void SimAgent::clear() {

std::multimap<float, SimSchedule*>::iterator i;
for (i = Events.begin(); i != Events.end(); i++) {
	i->second->Owner = NULL;
      delete i->second;
  }
  Events.clear();
  setEventTime(SIM_INFINITY);

}

void SimAgent::handler(float Time, SimProcess *process) {

  if (Events.empty()) return;
  SimSchedule *e = Events.begin()->second;
  e->handler(Time, process);
  // recurrent event is expected to reschedule it self
  if (e->Owner == NULL) delete e;

}

/* SimAgentManager */

SimAgentManager::SimAgentManager() {

  Owner = NULL;

}

SimAgentManager::~SimAgentManager() { }

SimChangeOwnerEvent::SimChangeOwnerEvent(float time, SimID newowner, SimDistribution *rep)

  : SimSchedule(time)

{

  NewOwner = newowner;
  Repetition = rep;

}

SimChangeOwnerEvent::~SimChangeOwnerEvent() {

  if (Repetition != NULL) delete Repetition;

}

void SimChangeOwnerEvent::handler(float time, SimProcess *proc) {

  if (owner() == NULL) return;
  if (owner()->owner() != NULL)
      owner()->owner()->removeAgent(owner());
  SimAgent *newowner = proc->agentWithID(NewOwner);
  if (newowner != NULL)
      newowner->addAgent(owner());
  if (proc != NULL) proc->log(time, owner(), this);
  if (newowner == NULL)
      proc->addAgent(owner());
  if (Repetition != NULL) {
      // explicitly request for rescheduling
      setEventTime(Repetition->draw()+time);
      owner()->schedule(this);
  }
  else
      owner()->unschedule(this);

}

SimDieEvent::SimDieEvent(float time)

  : SimSchedule(time)

{ }

SimDieEvent::~SimDieEvent() { }

void SimDieEvent::handler(float time, SimProcess *proc) {

  owner()->die(proc);
  if (proc != NULL) proc->log(time, owner(), this);

} </content> <use name=“simagent.h”/>