1#ifndef HALCHECK_LIB_TRIE_HPP
2#define HALCHECK_LIB_TRIE_HPP
11#include <halcheck/lib/functional.hpp>
12#include <halcheck/lib/iterator.hpp>
13#include <halcheck/lib/memory.hpp>
14#include <halcheck/lib/type_traits.hpp>
24namespace halcheck {
namespace lib {
33template<
typename K,
typename V,
typename Hash = std::hash<K>>
61 explicit trie(V value, I first, I last)
62 : _value(new V(
std::move(value))), _children(new
std::unordered_map<K,
trie>(
std::move(first),
std::move(last))) {
116 return drop(lib::begin(range), lib::end(range));
132 for (; first != last; ++first) {
133 auto it = output.find(*first);
134 if (it == output.end())
170 auto current = &output;
172 for (; first != last; ++first) {
175 current = &(*current->_children)[*first];
194 return set(lib::begin(range), lib::end(range), std::move(value));
212 explicit iterator(
typename std::unordered_map<K, trie, Hash>::const_iterator base) : _base(std::move(base)) {}
219 reference operator*()
const {
return *_base; }
221 pointer operator->()
const {
return _base.operator->(); }
224 friend bool operator==(
const iterator &lhs,
const iterator &rhs) {
return lhs._base == rhs._base; }
226 typename std::unordered_map<K, trie, Hash>::const_iterator _base;
251 bool empty()
const {
return _children.empty(); }
260 return iterator(_children->find(key));
A utility class for easily defining new iterators.
Definition interface.hpp:40
Represents a pointer to a child trie.
Definition trie.hpp:200
iterator begin() const
Returns an iterator to the first child.
Definition trie.hpp:233
trie(V value, I first, I last)
Constructs a trie with a given value and set of children.
Definition trie.hpp:61
iterator find(const K &key) const
Gets an iterator to the child indicated by the given key.
Definition trie.hpp:258
trie set(I first, I last, V value) const
Constructs a new trie with a specific value replaced.
Definition trie.hpp:168
bool empty() const
Determines whether this trie has any children.
Definition trie.hpp:251
trie drop(const R &range) const
Gets a specific subtree.
Definition trie.hpp:115
trie()=default
Constructs a trie where every node is assigned the same value.
const V & operator*() const
Gets the value associated with the root node of this trie.
Definition trie.hpp:83
trie drop(I first, I last) const
Gets a specific subtree.
Definition trie.hpp:130
iterator end() const
Returns an iterator to one past the last child.
Definition trie.hpp:239
const V & operator[](const R &range) const
Gets the value associated with a specific node.
Definition trie.hpp:101
trie(V value, R &&range)
Constructs a trie with a given value and set of children.
Definition trie.hpp:77
std::size_t size() const
Returns the number of children in this trie.
Definition trie.hpp:245
trie set(const R &range, V value) const
Constructs a new trie with a specific value replaced.
Definition trie.hpp:193
trie drop(const K &key) const
Gets a specific subtree.
Definition trie.hpp:148
An implementation of a trie. Semantically, this corresponds to a function .
Definition trie.hpp:34
lib::effect_result_t< T > fallback(T args)
Invokes the fallback behaviour for an effect.
typename std::iterator_traits< I >::reference iter_reference_t
The return type of operator* for an iterator.
Definition base.hpp:24
lib::iter_reference_t< lib::iterator_t< R > > range_reference_t
The type returned by operator* for a range type's iterators.
Definition range.hpp:340
#define HALCHECK_REQUIRE(...)
Expands to a template argument that is only valid if the given argument evaluates to true.
Definition type_traits.hpp:24
An implementation of std::is_invocable_r.
Definition invoke.hpp:54
Determines whether the given type is a range.
Definition range.hpp:158