Simpact Cyan
Population based event driven simulation using mNRM
eventvariablefiretime.h
1 #ifndef EVENTVARIABLEFIRETIME_H
2 
3 #define EVENTVARIABLEFIRETIME_H
4 
5 #include "simpactevent.h"
6 #include <assert.h>
7 
8 // Helper class which can come in handy to avoid the virtual inheritance scenario
9 class EventVariableFireTime_Helper
10 {
11 public:
12  EventVariableFireTime_Helper() { m_fireTime = -1; m_alpha = -1; }
13  ~EventVariableFireTime_Helper() { }
14 
15  void checkFireTime(double t) { assert(std::abs(m_fireTime - t) < 1e-8); }
16  void setFireTime(double tFire);
17  double getFireTime() const { assert(m_fireTime); return m_fireTime; }
18 
19  double getNewInternalTimeDifference(GslRandomNumberGenerator *pRndGen, const State *pState);
20  double calculateInternalTimeInterval(const State *pState, double t0, double dt, const EventBase *pEvt);
21  double solveForRealTimeInterval(const State *pState, double Tdiff, double t0, const EventBase *pEvt);
22 private:
23  void calculateScaleFactor(double currentTime, const EventBase *pEvt);
24 
25  double m_fireTime;
26  double m_alpha;
27 };
28 
29 // This is basically just a proxy to the helper class, but it may come in handy to use as an event
30 // base class
31 class EventVariableFireTime : public SimpactEvent
32 {
33 public:
34  EventVariableFireTime() : SimpactEvent() { }
35  EventVariableFireTime(Person *pPerson) : SimpactEvent(pPerson) { }
36  EventVariableFireTime(Person *pPerson1, Person *pPerson2) : SimpactEvent(pPerson1, pPerson2) { }
37  ~EventVariableFireTime() { }
38 
39  void checkFireTime(double t) { m_helper.checkFireTime(t); }
40 
41  void fire(State *pState, double t) { m_helper.checkFireTime(t); }
42  void setFireTime(double tFire) { m_helper.setFireTime(tFire); }
43  double getFireTime() const { return m_helper.getFireTime(); }
44 private:
45  double getNewInternalTimeDifference(GslRandomNumberGenerator *pRndGen, const State *pState) { return m_helper.getNewInternalTimeDifference(pRndGen, pState); }
46  double calculateInternalTimeInterval(const State *pState, double t0, double dt) { return m_helper.calculateInternalTimeInterval(pState, t0, dt, this); }
47  double solveForRealTimeInterval(const State *pState, double Tdiff, double t0) { return m_helper.solveForRealTimeInterval(pState, Tdiff, t0, this); }
48 
49  EventVariableFireTime_Helper m_helper;
50 };
51 
52 // The necessary functions are very simple, can easily be done inline
53 inline void EventVariableFireTime_Helper::setFireTime(double tFire)
54 {
55  assert(tFire > 0);
56 
57  m_fireTime = tFire;
58  m_alpha = -1; // marker to recalculate
59 }
60 
61 inline double EventVariableFireTime_Helper::getNewInternalTimeDifference(GslRandomNumberGenerator *pRndGen, const State *pState)
62 {
63  assert(m_fireTime > 0);
64  assert(m_alpha < 0);
65 
66  // We're going to transform this fixed number into the full duration in the hazard
67  // calculation
68  return 1.0; // so initially, dT = 1
69 }
70 
71 inline double EventVariableFireTime_Helper::calculateInternalTimeInterval(const State *pState, double t0, double dt, const EventBase *pEvt)
72 {
73  if (m_alpha < 0) // marker to indicate that recalculation is needed
74  calculateScaleFactor(t0, pEvt);
75 
76  double dT = dt * m_alpha;
77  return dT;
78 }
79 
80 inline double EventVariableFireTime_Helper::solveForRealTimeInterval(const State *pState, double Tdiff, double t0, const EventBase *pEvt)
81 {
82  if (m_alpha < 0) // marker to indicate that recalculation is needed
83  calculateScaleFactor(t0, pEvt);
84 
85  double dt = Tdiff/m_alpha;
86  return dt;
87 }
88 
89 inline void EventVariableFireTime_Helper::calculateScaleFactor(double currentTime, const EventBase *pEvt)
90 {
91  assert(m_alpha < 0);
92  assert(pEvt);
93 
94  double dTleft = pEvt->getInternalTimeLeft();
95  assert(dTleft > 0 && dTleft <= 1.0);
96 
97  double dtLeft = m_fireTime - currentTime;
98  assert(dtLeft > 0);
99 
100  m_alpha = dTleft/dtLeft;
101 }
102 
103 #endif // EVENTVARIABLEFIRETIME_H
104 
This class both describes the simulation state and contains the core algorithm (as shown on the main ...
Definition: state.h:40
This class allows you to generate random numbers, and uses the GNU Scientific Library for this...
Definition: gslrandomnumbergenerator.h:16
This is the base class for events in the mNRM algorithm.
Definition: eventbase.h:62