phylopomp
Phylodynamics for POMPs
Loading...
Searching...
No Matches
genealogy.h
Go to the documentation of this file.
1// -*- C++ -*-
2// GENEALOGY class
3
4#ifndef _GENEALOGY_H_
5#define _GENEALOGY_H_
6
7#include <utility>
8#include <stdexcept>
9
10#include "nodeseq.h"
11#include "internal.h"
12
13static const size_t MEMORY_MAX = (1<<28); // 256MB
14
16
19class genealogy_t : public nodeseq_t {
20
21private:
22
23 // GENEALOGY member data:
24 // - a counter of serial numbers
25 // - an initial time
26 // - the current time
27 // - a sequence of nodes
28
36 size_t _ndeme;
37
38 const static name_t magic = 1123581321;
39
40private:
41
43 name_t unique (void) {
44 name_t u = _unique;
45 _unique++;
46 return u;
47 };
48
50 void clean (void) {
51 _unique = 0;
52 _ndeme = 0;
53 _t0 = _time = R_NaReal;
54 };
55
56public:
57
59 size_t ndeme (void) const {
60 return _ndeme;
61 };
62
63 size_t& ndeme (void) {
64 return _ndeme;
65 };
66
67public:
68
69 // SERIALIZATION
71 size_t bytesize (void) const {
72 return 3*sizeof(name_t) +
73 2*sizeof(slate_t) + nodeseq_t::bytesize();
74 };
75
76 friend raw_t* operator>> (const genealogy_t& G, raw_t* o) {
77 name_t A[3]; A[0] = magic; A[1] = G._unique; A[2] = name_t(G.ndeme());
78 slate_t B[2]; B[0] = G.timezero(); B[1] = G.time();
79 memcpy(o,A,sizeof(A)); o += sizeof(A);
80 memcpy(o,B,sizeof(B)); o += sizeof(B);
81 return reinterpret_cast<const nodeseq_t&>(G) >> o;
82 };
83
85 G.clean();
86 name_t A[3];
87 slate_t B[2];
88 memcpy(A,o,sizeof(A)); o += sizeof(A);
89 memcpy(B,o,sizeof(B)); o += sizeof(B);
90 if (A[0] != magic)
91 err("in %s: corrupted genealogy serialization.",__func__);
92 G._unique = A[1]; G.ndeme() = size_t(A[2]);
93 G.timezero() = B[0]; G.time() = B[1];
94 return o >> reinterpret_cast<nodeseq_t&>(G);
95 };
96
97public:
98 // CONSTRUCTORS
102 genealogy_t (double t0 = R_NaReal, size_t ndeme = 0) {
103 clean();
104 _time = _t0 = slate_t(t0);
105 _ndeme = ndeme;
106 };
107
109 o >> *this;
110 };
111
112 genealogy_t (SEXP o) {
113 if (LENGTH(o)==0)
114 err("in %s: cannot deserialize a NULL.",__func__);
115 PROTECT(o = AS_RAW(o));
116 RAW(o) >> *this;
117 UNPROTECT(1);
118 };
119
121 raw_t *o = new raw_t[G.bytesize()];
122 G >> o;
123 o >> *this;
124 delete[] o;
125 };
126
128 clean();
129 raw_t *o = new raw_t[G.bytesize()];
130 G >> o;
131 o >> *this;
132 delete[] o;
133 return *this;
134 };
135
141 clean();
142 };
143
145 slate_t& time (void) {
146 return _time;
147 };
148
149 slate_t time (void) const {
150 return _time;
151 };
152
154 return _t0;
155 };
156
157 slate_t timezero (void) const {
158 return _t0;
159 };
160
161public:
162
170 void lineage_count (double *tout, int *deme,
171 int *ell, int *sat, int *etype) const;
173 SEXP lineage_count (void) const;
174
176 void gendat (double *tout, int *anc, int *lin,
177 int *sat, int *type, int *deme,
178 int *index, int *child) const;
180 SEXP gendat (void) const;
181
183 size_t nsample (void) const {
184 size_t n = 0;
185 for (const node_t *p : *this) {
186 if (p->holds(blue)) n++;
187 }
188 return n;
189 };
190
192 size_t nroot (void) const {
193 size_t n = 0;
194 for (const node_t *p : *this) {
195 if (p->holds_own()) n++;
196 }
197 return n;
198 };
199
200public:
201
203 string_t yaml (string_t tab = "") const;
205 SEXP structure (void) const;
207 string_t newick (bool extended = true) const;
208
209public:
210
212 void valid (void) const {};
214 bool check_genealogy_size (size_t grace = 0) const {
215 static size_t maxq = MEMORY_MAX/(sizeof(node_t)+2*sizeof(ball_t));
216 bool ok = true;
217 if (size() > maxq+grace) {
218 err("maximum genealogy size exceeded!"); // #nocov
219 } else if (size() > maxq) {
220 ok = false; // #nocov
221 }
222 return ok;
223 };
224
225private:
226
231 name_t u = unique();
232 node_t *p = new node_t(u,_time);
233 ball_t *g = new ball_t(p,u,green,d);
234 p->green_ball() = g;
235 p->insert(g);
236 return p;
237 };
238
239public:
240
243 time() = t;
244 node_t *p = make_node(a->deme());
245 ball_t *b = new ball_t (p,p->uniq,black,d);
246 p->insert(b);
247 p->slate = time();
248 add(p,a);
249 return b;
250 };
251
253 ball_t *b = new ball_t(p,unique(),black,d);
254 p->insert(b);
255 return b;
256 };
257
258 void death (ball_t *a, slate_t t) {
259 time() = t;
260 drop(a);
261 };
262
264 time() = t;
265 node_t *p = make_node();
266 ball_t *b = new ball_t (p,p->uniq,black,d);
267 p->insert(b);
268 p->slate = timezero();
269 push_front(p);
270 return b;
271 };
272
273 void sample (ball_t* a, slate_t t) {
274 time() = t;
275 node_t *p = make_node(a->deme());
276 ball_t *b = new ball_t (p,p->uniq,blue,a->deme());
277 p->insert(b);
278 p->slate = time();
279 add(p,a);
280 };
281
283 time() = t;
284 node_t *p = make_node(a->deme());
285 ball_t *b = new ball_t (p,p->uniq,blue,a->deme());
286 p->insert(b);
287 p->slate = time();
288 add(p,a);
289 drop(a);
290 };
291
292 void migrate (ball_t* a, slate_t t, name_t d = 0) {
293 time() = t;
294 node_t *p = make_node(a->deme());
295 p->slate = time();
296 add(p,a);
297 a->deme() = d;
298 };
299
300 void sample_migrate (ball_t* a, slate_t t, name_t d = 0) {
301 time() = t;
302 node_t *p = make_node(a->deme());
303 ball_t *b = new ball_t (p,p->uniq,blue,a->deme());
304 p->insert(b);
305 p->slate = time();
306 add(p,a);
307 a->deme() = d;
308 };
309
311 pocket_t *blacks = colored(black);
312 while (!blacks->empty()) {
313 ball_t *b = *(blacks->begin());
314 blacks->erase(b);
315 drop(b);
316 }
317 delete blacks;
318 return *this;
319 };
320
322 // erase deme information from black balls.
323 pocket_t *blacks = colored(black);
324 while (!blacks->empty()) {
325 ball_t *a = *(blacks->begin());
326 a->deme() = undeme;
327 blacks->erase(a);
328 }
329 delete blacks;
330 // erase deme information from nodes.
331 for (node_t *p : *this) {
332 p->deme() = undeme;
333 }
334 // drop superfluous nodes (holding just one ball).
335 comb();
336 ndeme() = 0;
337 return *this;
338 };
339
342 void curtail (slate_t tnew, slate_t troot);
343
344private:
345
346 void reuniqify (name_t shift);
347
348public:
349
355 genealogy_t& operator+= (const genealogy_t& other);
356
358 void insert_zlb (void) {
359 for (node_t *p : *this) {
360 if (p->holds(green) && p->holds(blue)) {
361 assert(!p->holds(black)); // genealogy should have already been pruned
362 ball_t *b = p->last_ball();
363 assert(b->is(blue));
364 node_t *q = make_node(p->deme());
365 q->slate = p->slate;
366 swap(q->green_ball(),b);
367 push_back(q);
368 }
369 }
370 sort();
371 };
372
373 void drop_zlb (void) {
374 for (node_t *p : *this) {
375 if (!p->holds_own() &&
376 p->slate == p->parent()->slate &&
377 p->deme() == p->parent()->deme()) {
378 while (!p->empty()) {
379 ball_t *b = p->last_ball();
380 p->erase(b); p->parent()->insert(b);
381 }
382 detach(p);
383 }
384 }
385 };
386
387private:
388
391 void repair_tips (void);
393 void repair_roots (void) {
394 node_nit j = begin();
395 while (j != end()) {
396 if ((*j)->holds_own() && (*j)->slate > timezero()) {
397 node_t *q = make_node();
398 q->slate = timezero();
399 attach(q,*j);
400 push_front(q);
401 }
402 j++;
403 }
404 sort();
405 };
406
409 node_t *scan_branch (string_t::const_iterator b, string_t::const_iterator e);
410
411public:
412
414 genealogy_t& parse (const string_t& s);
415
416};
417
418#endif
@ green
Definition ball.h:12
@ black
Definition ball.h:12
@ blue
Definition ball.h:12
static const name_t undeme
Definition ball.h:15
Balls function as pointers.
Definition ball.h:27
name_t deme(void) const
view deme
Definition ball.h:84
bool is(color_t c) const
is a given ball of the given color?
Definition ball.h:115
Encodes a genealogy.
Definition genealogy.h:19
void repair_roots(void)
roots are added at zero time if needed
Definition genealogy.h:393
size_t & ndeme(void)
number of demes
Definition genealogy.h:63
slate_t time(void) const
view current time.
Definition genealogy.h:149
size_t nsample(void) const
number of samples
Definition genealogy.h:183
~genealogy_t(void)
destructor
Definition genealogy.h:140
SEXP structure(void) const
R list description.
Definition structure.cc:85
void clean(void)
clean up
Definition genealogy.h:50
void drop_zlb(void)
drop all zero-length branches
Definition genealogy.h:373
void reuniqify(name_t shift)
shifts names to avoid overlap
Definition sum.cc:21
void valid(void) const
check the validity of the genealogy.
Definition genealogy.h:212
genealogy_t(SEXP o)
constructor from RAW SEXP (containing binary serialization)
Definition genealogy.h:112
genealogy_t & operator=(const genealogy_t &G)
copy assignment operator
Definition genealogy.h:127
void death(ball_t *a, slate_t t)
death
Definition genealogy.h:258
SEXP lineage_count(void) const
lineage count and saturation
Definition lineages.cc:80
genealogy_t & prune(void)
prune the tree (drop all black balls)
Definition genealogy.h:310
size_t bytesize(void) const
size of serialized binary form
Definition genealogy.h:71
genealogy_t(double t0=R_NaReal, size_t ndeme=0)
Definition genealogy.h:102
string_t yaml(string_t tab="") const
human/machine-readable info
Definition yaml.cc:64
size_t ndeme(void) const
number of demes
Definition genealogy.h:59
genealogy_t(const genealogy_t &G)
copy constructor
Definition genealogy.h:120
bool check_genealogy_size(size_t grace=0) const
check the size of the genealogy (to prevent memory exhaustion).
Definition genealogy.h:214
slate_t timezero(void) const
get zero time.
Definition genealogy.h:157
ball_t * graft(slate_t t, name_t d)
graft a new lineage into deme d
Definition genealogy.h:263
void migrate(ball_t *a, slate_t t, name_t d=0)
movement into deme d
Definition genealogy.h:292
slate_t _time
The current time.
Definition genealogy.h:34
SEXP gendat(void) const
genealogy information in list format
Definition gendat.cc:60
ball_t * birth(node_t *p, name_t d)
birth of second or subsequent sibling into deme d
Definition genealogy.h:252
genealogy_t & operator+=(const genealogy_t &other)
merges two genealogies, adjusting time, t0, and ndeme as needed
Definition sum.cc:30
size_t _ndeme
The number of demes (excluding the undeme).
Definition genealogy.h:36
void insert_zlb(void)
insert zero-length branches for samples where needed
Definition genealogy.h:358
slate_t & timezero(void)
view/set zero time.
Definition genealogy.h:153
void sample_death(ball_t *a, slate_t t)
insert a sample node and simultaneously terminate the lineage
Definition genealogy.h:282
genealogy_t(raw_t *o)
constructor from serialized binary form
Definition genealogy.h:108
slate_t & time(void)
view/set current time.
Definition genealogy.h:145
genealogy_t & parse(const string_t &s)
Parse a Newick string and create the indicated genealogy.
Definition parse.cc:131
node_t * make_node(name_t d=undeme)
Definition genealogy.h:229
void curtail(slate_t tnew, slate_t troot)
Definition curtail.cc:11
friend raw_t * operator>>(const genealogy_t &G, raw_t *o)
binary serialization
Definition genealogy.h:76
void sample_migrate(ball_t *a, slate_t t, name_t d=0)
insert a sample node and simultaneously migrate the lineage
Definition genealogy.h:300
static const name_t magic
Definition genealogy.h:38
name_t unique(void)
get the next unique name
Definition genealogy.h:43
void sample(ball_t *a, slate_t t)
insert a sample node
Definition genealogy.h:273
slate_t _t0
The initial time.
Definition genealogy.h:32
name_t _unique
The next unique name.
Definition genealogy.h:30
size_t nroot(void) const
number of roots
Definition genealogy.h:192
genealogy_t(genealogy_t &&)=default
move constructor
ball_t * birth(ball_t *a, slate_t t, name_t d)
birth into deme d
Definition genealogy.h:242
genealogy_t & obscure(void)
erase all deme information
Definition genealogy.h:321
string_t newick(bool extended=true) const
put genealogy at current time into Newick format.
Definition newick.cc:94
void repair_tips(void)
Definition parse.cc:9
node_t * scan_branch(string_t::const_iterator b, string_t::const_iterator e)
Definition parse.cc:101
Encodes a genealogical node.
Definition node.h:21
node_t * parent(void) const
Definition node.h:115
name_t deme(void) const
view deme
Definition node.h:96
name_t uniq
Definition node.h:32
ball_t * green_ball(void) const
pointer to my green ball
Definition node.h:88
void insert(ball_t *a)
insert a ball into the pocket of a node
Definition node.h:156
slate_t slate
Definition node.h:33
bool holds_own(void) const
Definition node.h:118
A sequence of nodes.
Definition nodeseq.h:17
void detach(node_t *p)
Definition nodeseq.h:179
void comb(void)
Definition nodeseq.h:226
void sort(void)
order nodes in order of increasing time
Definition nodeseq.h:103
void attach(node_t *p, node_t *q)
Definition nodeseq.h:174
size_t bytesize(void) const
size of serialized binary form
Definition nodeseq.h:38
void drop(ball_t *a)
Definition nodeseq.h:192
void swap(ball_t *a, ball_t *b)
swap balls a and b, wherever they lie
Definition nodeseq.h:164
pocket_t * colored(color_t col) const
Get all balls of a color.
Definition nodeseq.h:121
void add(node_t *p, ball_t *a)
Definition nodeseq.h:184
A pocket is a set of balls.
Definition pocket.h:30
ball_t * last_ball(void) const
retrieve the last ball
Definition pocket.h:126
bool holds(ball_t *b) const
does this node hold the given ball?
Definition pocket.h:109
static const size_t MEMORY_MAX
Definition genealogy.h:13
Rbyte raw_t
Definition internal.h:52
size_t name_t
Definition internal.h:54
#define err(...)
Definition internal.h:18
double slate_t
Definition internal.h:53
static const int deme
Definition lbdp.cc:7
#define ell
Definition lbdp_pomp.c:11
#define n
Definition lbdp_pomp.c:9
std::list< node_t * >::iterator node_nit
Definition nodeseq.h:13