emplace support on hashtables

master
Daniel Kolesa 2015-06-15 02:09:53 +01:00
parent 1ae3957e5c
commit 8ce2e67e36
2 changed files with 28 additions and 0 deletions

View File

@ -50,6 +50,8 @@ public:
HashRange(Chain **ch, octa::Size n): p_chains(ch), p_num(n) {
advance();
}
HashRange(Chain **ch, Chain *node, octa::Size n): p_chains(ch),
p_node(node), p_num(n) {}
HashRange(const HashRange &v): p_chains(v.p_chains), p_node(v.p_node),
p_num(v.p_num) {}
@ -230,6 +232,27 @@ namespace detail {
return (insert(h, key) = val);
}
template<typename ...Args>
octa::Pair<Range, bool> emplace(Args &&...args) {
E elem(octa::forward<Args>(args)...);
octa::Size h = get_hash()(B::get_key(elem)) & (p_size - 1);
Chain *found = nullptr;
bool ins = true;
for (Chain *c = p_data.first()[h]; c; c = c->next) {
if (get_eq()(B::get_key(elem), B::get_key(c->value))) {
found = c;
ins = false;
break;
}
}
if (!found) {
found = insert(h);
B::swap_elem(found->value, elem);
}
return octa::make_pair(Range(&p_data.first()[h + 1], found,
bucket_count() - h - 1), ins);
}
float load_factor() const { return float(p_len) / p_size; }
float max_load_factor() const { return p_maxlf; }
void max_load_factor(float lf) { p_maxlf = lf; }

View File

@ -107,6 +107,11 @@ public:
return p_table.insert(h, octa::move(key));
}
template<typename ...Args>
octa::Pair<Range, bool> emplace(Args &&...args) {
return p_table.emplace(octa::forward<Args>(args)...);
}
octa::Size erase(const K &key) {
if (p_table.remove(key)) return 1;
return 0;