C++ Logo

std-discussion

Advanced search

Re: C++17 std::hash disabled specializations

From: Edward Diener <eldlistmailingz_at_[hidden]>
Date: Wed, 15 Apr 2020 11:58:09 -0400
On 4/15/2020 11:42 AM, Daniel Krügler via Std-Discussion wrote:
> Am Mi., 15. Apr. 2020 um 16:13 Uhr schrieb Edward Diener via
> Std-Discussion <std-discussion_at_[hidden]>:
>>
>> In C++17 if a std::hash specialization for a key is not provided and is
>> therefore considered a disabled specialization, is it a compiler error
>> if an unordered associate container is instantiated with that key ?
>>
>> As an example:
>>
>> struct MyStruct
>> {
>> int x;
>> long y;
>> MyStruct(int a, long b) : x(a), y(b) {}
>> };
>>
>> /* No std::hash specialization is provided for MyStruct */
>>
>> MyStruct my1(1,2);
>>
>> std::unordered_set<MyStruct> oname;
>> oname.insert(my1);
>>
>> Should the code cause a compilation error in C++17 and above ?
>
> The standard says for a disabled specialization:
>
> "these values are false: is_default_constructible_v<H>,
> is_copy_constructible_v<H>, is_move_constructible_v<H>,
> is_copy_assignable_v<H>, and is_move_assignable_v<H>. Disabled
> specializations of hash are not function object types (23.14)."
>
> For unordered associative containers, C++17 imposes the requirement
>
> "Hash shall be a unary function
> object type such that the
> expression hf(k) has type
> size_t."
>
> For the default constructor the requirements
>
> "hasher and
> key_equal are
> DefaultConstructible."
>
> are imposed.
>
> Technically these are pre-conditions whose violation would lead to UB.
> But given the above mentioned characteristics of disabled hash
> specializations I would expect sane implementations to make the code
> ill-formed, e.g. when the constructor of the set is invoked or the
> when insert is called.
>
> I'm not sure whether this actually answers your question, though. Can
> you elaborate?

Your saying that it is UB in C++17 and above implies that the code need
not produce a compiler error according to the C++ standard. My other
respondent quoted parts of the standard which implies that it is a
compiler error. I am aware that UB, which can occur at run-time, and a
compilation error, which occurs at compile time, are two very different
things.

There is a unit test for such code which I am encountering which says
that the code should be producing a compilation error. With a particular
compiler I am testing it does not produce this compilation error where
with all other compilers I am testing it does produce a compilation
error. I want to justify a bug report to the compiler which does not
produce a compilation error in C++17 mode by showing that it should be
producing such a compilation error. This may cause them to fix their
compiler. But if indeed it is a UB situation than that compiler is doing
nothing wrong and the unit test is incorrect.

Received on 2020-04-15 11:01:09