hash table cleanups

master
Daniel Kolesa 2015-06-18 01:41:00 +01:00
parent 7cf50febd9
commit b20a6ec38e
2 changed files with 24 additions and 21 deletions

View File

@ -143,6 +143,7 @@ namespace detail {
typename A, /* allocator */ typename A, /* allocator */
bool Multihash bool Multihash
> struct Hashtable { > struct Hashtable {
private:
static constexpr octa::Size CHUNKSIZE = 64; static constexpr octa::Size CHUNKSIZE = 64;
using Chain = octa::detail::HashChain<E>; using Chain = octa::detail::HashChain<E>;
@ -176,6 +177,7 @@ namespace detail {
float p_maxlf; float p_maxlf;
public:
const H &get_hash() const { return p_data.second().second().first(); } const H &get_hash() const { return p_data.second().second().first(); }
const C &get_eq() const { return p_data.second().second().second(); } const C &get_eq() const { return p_data.second().second().second(); }
@ -329,6 +331,22 @@ namespace detail {
return B::get_data(c->value); return B::get_data(c->value);
} }
T &access_or_insert(const K &key) {
octa::Size h;
T *v = access_base(key, h);
if (v) return *v;
rehash_ahead(1);
return insert(h, key);
}
T &access_or_insert(K &&key) {
octa::Size h;
T *v = access_base(key, h);
if (v) return *v;
rehash_ahead(1);
return insert(h, octa::move(key));
}
octa::Size remove(const K &key) { octa::Size remove(const K &key) {
if (!p_len) return 0; if (!p_len) return 0;
octa::Size olen = p_len; octa::Size olen = p_len;
@ -389,16 +407,9 @@ namespace detail {
return NULL; return NULL;
} }
T *access(const K &key) const { T &access(const K &key) const {
octa::Size h; octa::Size h;
return access_base(key, h); return *access_base(key, h);
}
T &access(const K &key, const T &val) {
octa::Size h;
T *found = access_base(key, h);
if (found) return *found;
return (insert(h, key) = val);
} }
template<typename ...Args> template<typename ...Args>

View File

@ -171,25 +171,17 @@ public:
} }
T &at(const K &key) { T &at(const K &key) {
return *p_table.access(key); return p_table.access(key);
} }
const T &at(const K &key) const { const T &at(const K &key) const {
return *p_table.access(key); return p_table.access(key);
} }
T &operator[](const K &key) { T &operator[](const K &key) {
octa::Size h; return p_table.access_or_insert(key);
T *v = p_table.access_base(key, h);
if (v) return *v;
p_table.rehash_ahead(1);
return p_table.insert(h, key);
} }
T &operator[](K &&key) { T &operator[](K &&key) {
octa::Size h; return p_table.access_or_insert(octa::move(key));
T *v = p_table.access_base(key, h);
if (v) return *v;
p_table.rehash_ahead(1);
return p_table.insert(h, octa::move(key));
} }
template<typename ...Args> template<typename ...Args>