On Monday, 11 June 2018 15:49:10 UTC+3, Frank Tetzel wrote:
>
> It seems to always be (inserted_elements * 2) - 1.
> When adding 2 elements, it hashes 3 times. When adding 1 element, it
> only hashes once. What is happening here? Why is the hash calculated
> twice? What is so special about the last or first element?
>
> Btw, I'm running gcc 8.1.1.
Standard-library cashes potentially slow and throwing hashes.
For example in first standard library that happened under my hand
right now (and it seems at least 4 years old) I see in its
bits/hashtable.h:
template<typename _Tp, typename _Hash>
using __cache_default
= __not_<__and_<// Do not cache for fast hasher.
__is_fast_hash<_Hash>,
// Mandatory to make local_iterator default
// constructible and assignable.
is_default_constructible<_Hash>,
is_copy_assignable<_Hash>,
// Mandatory to have erase not throwing.
__detail::__is_noexcept_hash<_Tp, _Hash>>>;
So it does not cache your hashes and instead calls the hash function
when it needs to. It needs to do so so few times because you did
reserve, otherwise it would likely need to call it more times.
Also if you want your MyHash to be "slow" but noexcept then in the
standard library that I see it can be done by disabling its
copy-assignment:
MyHash& operator=(const MyHash&) = delete;
Good to know when you happen to have relatively slow non-throwing
hasher. ;)