summaryrefslogtreecommitdiff
path: root/code/core/event.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'code/core/event.cpp')
-rw-r--r--code/core/event.cpp128
1 files changed, 128 insertions, 0 deletions
diff --git a/code/core/event.cpp b/code/core/event.cpp
new file mode 100644
index 0000000..cb6f5ff
--- /dev/null
+++ b/code/core/event.cpp
@@ -0,0 +1,128 @@
+#include "simulate.h"
+
+#include "event.h"
+
+void Event::execute() {
+ switch (type) {
+ case 0:
+ ((InternalSpike*) this)->execute();
+ break;
+
+ case 1:
+ ((ExternalSpike*) this)->execute();
+ break;
+
+ case 2:
+ ((ExternalNoise*) this)->execute();
+ break;
+
+ case 3:
+ ((IntrinsicNeuron*) this)->execute();
+ break;
+
+ case 4:
+ ((VirtualEvent*) this)->vexecute();
+ break;
+ }
+}
+
+void Event::free() {
+ switch (type) {
+ case 0:
+ delete (InternalSpike*) this;
+ break;
+
+ case 1:
+ delete (ExternalSpike*) this;
+ break;
+
+ case 2:
+ delete (ExternalNoise*) this;
+ break;
+
+ case 3:
+ delete (IntrinsicNeuron*) this;
+ break;
+
+ case 4:
+ delete (VirtualEvent*) this;
+ break;
+ }
+}
+
+// comparison of two events regarding their order in the event list; spike events are processed prior to non-spike events (as spikes are incoming and non-spike are intrinsic and depending on all events up to the present)
+bool Event::operator>(Event &e) {
+ return (time > e.time) || ((time == e.time) && (type > e.type));
+}
+
+void Spike::execute() {
+ double nextEventTime = s.neurons[dst].processCurrent(time, current);
+
+ // check if there is an event to occur
+ if (nextEventTime != INFINITY)
+ s.addEvent(new IntrinsicNeuron(nextEventTime, dst));
+}
+
+void ExternalSpike::execute() {
+ // exec common spike code
+ ((Spike *) this)->execute();
+}
+
+void InternalSpike::execute() {
+ // the spike has to be registered as delieverd in the sending synapse
+ synapse->lastSpike = time;
+ if (synapse->firstSpike == -INFINITY)
+ synapse->firstSpike = time;
+
+ // exec common spike code
+ ((Spike *) this)->execute();
+
+ // synaptic scaling
+ s.neurons[dst].normalizeWeight(g.sumWeight);
+}
+
+void IntrinsicNeuron::execute() {
+ // check if a spike does occur
+ bool spikeDoesOccur;
+ double nextEventTime = s.neurons[dst].generateSpike(time, spikeDoesOccur);
+
+ // check if a spike should be generated
+ if (!spikeDoesOccur)
+ return;
+
+ // add next intrinsic event
+ if (nextEventTime != INFINITY)
+ s.addEvent(new IntrinsicNeuron(nextEventTime, dst));
+
+ // create the spike for every neuron where it will be recieved
+ for (SynapseDstList::iterator i = s.neurons[dst].sout.begin(); i != s.neurons[dst].sout.end(); i++) {
+ double ntime = time, ncurrent;
+ i->computePostsynapticPulse(ntime, ncurrent);
+ s.addEvent(new InternalSpike(ntime, i->dst, ncurrent, &(*i)));
+ }
+
+ // check if we should output a spike of this neuron
+ for (s.spikeOIfList.iterator i = s.spikeOIfList.begin(); i != s.spikeOIfList.end(); i++)
+ if (i->isContained(dst)) {
+ SpikeMUX s(dst, time);
+ i->pushObject(s);
+ }
+
+ // bin spikes
+ for (std::set<Bin*>::iterator bin = s.binSets.begin(); bin != s.to.traceBinSets.end(); bin++)
+ (*bin)->bin(dst);
+}
+
+void ExternalNoise::execute() {
+ // pick a random neuron to send noise to (using a temporary event)
+ s.addEvent(new ExternalSpike(time, rand() % (s.numNeurons * 4 / 5), g.en_current));
+
+ // select the next timepoint from a poisson process
+ s.addEvent(new ExternalNoise(time - (log(1.0 - drand48()) / (g.en_freq * s.numNeurons))));
+}
+
+virtual void GlobalUpdate::vexecute() {
+ static const double td = 0.001;
+ g.evolve(td);
+ s.addEvent(new GlobalUpdate(time + td));
+}
contact: Jan Huwald // Impressum