-
Notifications
You must be signed in to change notification settings - Fork 33
Expand file tree
/
Copy pathReproductionQueue.h
More file actions
96 lines (79 loc) · 2.29 KB
/
Copy pathReproductionQueue.h
File metadata and controls
96 lines (79 loc) · 2.29 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
#pragma once
#include "../Organism.h"
#include <deque>
#include <functional>
namespace sgpmode {
// TODO - tests!
// Encapsulates information about a reproduction request
struct ReproEvent {
emp::Ptr<Organism> org; // Organism to reproduce
emp::WorldPosition pos; // Location of reproduction event in world
bool valid = true;
// size_t event_id = 0;
ReproEvent() = default;
ReproEvent(
emp::Ptr<Organism> in_org,
const emp::WorldPosition& in_pos,
bool in_valid=true
) : org(in_org), pos(in_pos), valid(in_valid) { }
};
/*
Tracks organisms queued for reproduction.
*/
class ReproductionQueue {
public:
using fun_repro_org_t = std::function<void(ReproEvent&)>;
protected:
// TODO - queue vector
emp::vector<ReproEvent> queue;
fun_repro_org_t fun_reproduce_org;
// TODO - set tracking what is in the queue
// std::unordered_set in
// TODO - next_id
// size_t next_id = 0; // id to assign to next reproduction event (will be unique with respect to all other currently queued events)
public:
void Clear() {
queue.clear();
}
size_t GetSize() const {
return queue.size();
}
const emp::vector<ReproEvent>& GetQueue() const {
return queue;
}
void SetReproduceOrgFun(fun_repro_org_t fun) {
fun_reproduce_org = fun;
}
void Invalidate(size_t queue_pos) {
emp_assert(queue_pos < queue.size());
queue[queue_pos].valid = false;
}
// Add organism to queue, return organism's queue id (valid until queue is processed)
size_t Enqueue(
emp::Ptr<Organism> org_ptr,
const emp::WorldPosition& org_pos
) {
const size_t queue_id = queue.size();
queue.emplace_back(org_ptr, org_pos, true);
return queue_id;
}
// Queue must be processed all at once to avoid
// invalidating queue_ids.
// NOTE - could have world template and instead of a configurable functor.
// Why functor? Currently resetting repro
// template<typename WORLD_T>
// void Process(WORLD_T& world) {
void Process() {
for (ReproEvent& repro_info : queue) {
emp::Ptr<Organism> org_ptr = repro_info.org;
// If queued organism is dead or repro event has been invalidated,
// don't reproduce.
if (!repro_info.valid || org_ptr->GetDead()) {
continue;
}
fun_reproduce_org(repro_info);
}
Clear();
}
};
}