15 #ifndef _PASL_DATA_FTREE_H_
16 #define _PASL_DATA_FTREE_H_
28 class Top_item_deleter = chunkedseq::Pointer_deleter,
29 class Top_item_copier = chunkedseq::Pointer_deep_copier,
85 : tag(uninitialized_tag) { }
96 return tag == leaf_node_tag;
100 return tag == branch_node_tag;
104 assert(tag == uninitialized_tag);
118 template <
class Pred>
123 virtual void clear() = 0;
138 static leaf_node_p force(
node_p t) {
141 return (leaf_node_p)t;
159 :
node(), item(leaf) {
164 :
node(other), item(other.item) { }
172 template <
class Body>
194 static const int max_nb_branches = 3;
197 node_p branches[max_nb_branches];
200 static branch_node_p force(
node_p t) {
202 return (branch_node_p)t;
210 void set_branch(
int id,
node_p t) {
214 void refresh_cache() {
215 cached = algebra_type::identity();
216 for (
int i = 0; i < nb; i++)
217 cached = algebra_type::combine(cached, branches[i]->
get_cached());
240 :
node(other), nb(other.nb) {
259 for (
int i = 0; i < nb; i++)
263 template <
class Body>
265 for (
int i = 0; i < nb; i++)
278 new_node =
new branch_node(*branch_node::force(n));
283 template <
class Body>
304 static const int max_nb_digits = 4;
346 for (
int i = 0; i < nb; i++)
351 for (
int i = 0; i < nb; i++)
356 assert(ix >= 0 && ix < d.
size());
407 template <
typename Pred>
411 j = algebra_type::combine(j, i);
412 for (ix = 0; ix <
size(); ix++) {
413 j = algebra_type::combine(j, d[ix]->
get_cached());
421 static constexpr
int max_concat_nb_digits = max_nb_digits*3;
424 digit digits[3] = {d1, d2, d3};
425 for (
int k = 0; k < 3; k++) {
453 cached = algebra_type::combine(cached, d[i]->
get_cached());
457 template <
class Pred>
463 v = algebra_type::combine(v, n->
get_cached());
471 template <
class Body>
473 for (
int i = 0; i <
size(); i++)
502 cached = algebra_type::identity();
503 cached = algebra_type::combine(cached, fr.
get_cached());
505 cached = algebra_type::combine(cached, middle->
get_cached());
506 cached = algebra_type::combine(cached, bk.
get_cached());
529 : fr(fr), middle(middle), bk(bk) {
537 }
else if (sz == 1) {
539 }
else if (sz == 2) {
542 }
else if (sz == 3) {
554 middle =
new ftree();
580 middle =
new ftree();
592 cached = algebra_type::combine(cached, x->
get_cached());
598 cached = algebra_type::combine(cached, x->
get_cached());
601 middle =
new ftree();
620 if (algebra_type::has_inverse)
621 cached = algebra_type::combine(cached, algebra_type::inverse(
_back()->
get_cached()));
628 if (middle->
empty()) {
644 if (! algebra_type::has_inverse)
650 if (algebra_type::has_inverse)
651 cached = algebra_type::combine(algebra_type::inverse(
_front()->
get_cached()), cached);
658 if (middle->
empty()) {
671 if (! algebra_type::has_inverse)
681 for (
int i = (
int)d.
size() - 1; i >= 0; i--)
691 }
else if (bk->
empty()) {
695 }
else if (fr->
single()) {
701 }
else if (bk->
single()) {
731 template <
typename Pred>
733 assert(! f->
empty());
737 v.middle = f->
_back();
742 vfr = algebra_type::combine(vfr, i);
750 v.middle = f->
fr[ix];
754 vm = algebra_type::combine(vm, vfr);
762 tmp = algebra_type::combine(tmp, vfr);
764 ix = xs.find(p, tmp);
786 template <
class Pred>
788 assert(! ft->
empty());
804 assert(ft->
bk.
size() > 0);
809 return leaf_node::force(
_back());
813 return leaf_node::force(
_front());
816 template <
class Body>
838 assert(
_back()->is_leaf());
844 assert(
_front()->is_leaf());
849 template <
class Pred>
857 template <
typename Pred>
867 return app3(fr, d, bk);
884 if (middle != NULL &&
deep())
897 class Cached_measure,
898 class Top_item_deleter,
899 class Top_item_copier,
900 template<
class Item,
int Capacity,
class Item_alloc>
class Chunk_struct,
903 template <
class Pred>
904 const typename ftree< Top_item_base,
910 Size_access>::leaf_node_type*
911 ftree< Top_item_base,
917 Size_access>::node::down(
const node* t,
921 return ftree< Top_item_base,
927 Size_access>::leaf_node::cforce(t);
930 for (
int i = 0; i < nb; i++) {
933 v = algebra_type::combine(v, s->
get_cached());
935 return down(s, p, prefix);
946 class Cached_measure,
947 class Top_item_deleter = chunkedseq::Pointer_deleter,
948 class Top_item_copier = chunkedseq::Pointer_deep_copier,
960 using ftree_type =
ftree<Top_item_base, Chunk_capacity, Cached_measure,
961 Top_item_deleter, Top_item_copier, Chunk_struct,
1033 template <
class Body>
1042 std::swap(ft, other.
ft);
1045 template <
class Pred>
1047 const Top_item_base*& item)
const {
1054 template <
class M,
class Pred>
1064 item = r.middle->item;
1066 return algebra_type::combine(prefix, ft->
get_cached());
void _push_front(digit d)
void make_deep_copy(const ftree &other)
static digit concat3(digit d1, digit d2, digit d3)
measured_type search_for_chunk(const Pred &p, measured_type prefix, const Top_item_base *&item) const
typename cache_type::algebra_type algebra_type
leaf_node_type * __back() const
typename ftree_type::algebra_type algebra_type
measured_type split(M, const Pred &p, measured_type prefix, leaf_item_type &item, tftree &other)
void for_each(const Body &body) const
virtual measured_type get_cached() const =0
ftree< Top_item_base, Chunk_capacity, Cached_measure, Top_item_deleter, Top_item_copier, Chunk_struct, Size_access > ftree_type
Cached_measure cache_type
ftree(const ftree &other)
measured_type get_cached() const
Fixed-capacity ring buffer.
base::ringbuffer_ptr< base::heap_allocator< Item, Capacity+1 >> ringbuffer_ptr
void _push_front(node_p x)
leaf_item_type pop_front(M)
node_p operator[](size_type ix) const
branch_node_p back_three() const
void ___push_front(leaf_node_type *x)
leaf_item_type cback() const
node_p get_branch(int i) const
leaf_node(const leaf_item_type &leaf)
static node * make_deep_copy_tree(node *n)
static const node * down(const Pred &p, const digit *d, measured_type &prefix)
leaf_item_type pop_back(M)
leaf_node_type * __front() const
void push_front(node_p x)
void assign(branch_node_p x)
size_type find(const Pred &p, measured_type i) const
static const leaf_node * search_aux(const Pred &p, const ftree *start, measured_type &prefix)
value_type & front() const
void push_front(M, leaf_item_type item)
tftree(const tftree &other)
static split_rec_type split_rec(const Pred &p, measured_type i, ftree_p f)
void _for_each(const Body &body) const
measured_type get_cached() const
branch_node(node_p t0, node_p t1, node_p t2)
void for_each(const Body &body) const
void for_each(const Body &body) const
branch_node_p front_three() const
void push_back(const value_type &x)
static ftree_p app3(ftree_p fr, digit m, ftree_p bk)
value_type & back() const
leaf_item_type back() const
leaf_node(const leaf_node &other)
void push_front(const value_type &x)
typename cache_type::measure_type measure_type
ftree(digit fr, ftree_p middle, digit bk)
typename ftree_type::leaf_node leaf_node
static split_type split_aux(const Pred &p, measured_type prefix, ftree *f)
static void node_for_each(const Body &body, const node *n)
measured_type get_cached() const
typename ftree_type::measured_type measured_type
typename ftree_type::leaf_node_type leaf_node_type
Top_item_base * leaf_item_type
bool is_front(const digit *d) const
typename ftree_type::split_type split_type
void push_back(M, leaf_item_type item)
bool is_back(const digit *d) const
leaf_item_type front() const
typename ftree_type::leaf_item_type leaf_item_type
void concat(M, tftree &other)
void for_each(const Body &body) const
typename cache_type::measured_type measured_type
branch_node(node_p t0, node_p t1)
void swap(ringbuffer_ptr &other)
static const leaf_node_type * down(const node *t, const Pred &p, measured_type &prefix)
void _push_back(node_p x)
void make_deep_copy(digit &dst) const
static ftree * concatenate(ftree *fr, ftree *bk)
static const digit * down(const ftree *ft, const Pred &p, measured_type &prefix)
void ___push_back(leaf_node_type *x)
measured_type get_cached() const
measured_type get_cached() const
branch_node(const branch_node &other)