Эквивалентность перечислений и объединений в качестве шаблонных параметров
#include <type_traits>
template<auto T>
struct A {};
enum class E {
a = 0,
b = 0,
};
union U {
int a;
int b;
};
static_assert(std::is_same_v<A<E::a>, A<E::b>>);
static_assert(not std::is_same_v<A<U{.a=0}>, A<U{.b=0}>>);
Почему шаблонные классы с перечислениями с одинаковыми значениями в качестве шаблонных параметров считаются одинаковыми, а с объединениями - нет?
Ответы (1 шт):
Для того чтобы два шаблонных non-type аргумента, имеющих тип объединения (union) совпадали, они должны:
- иметь одинаковый тип,
- оба не иметь активных членов, либо оба иметь один и тот же активный член,
- значения активных членов должны совпадать.
Two template-ids are the same if
...
their corresponding non-type template-arguments are template-argument-equivalent (see below) after conversion to the type of the template-parameter,
...
Two values are template-argument-equivalent if they are of the same type and
...
they are of union type and either they both have no active member or they have the same active member and their active members are template-argument-equivalent,
...
В вашем случае два шаблонных аргумента имеют одинаковый тип объединения, значения активных членов совпадают, но объединения имеют разные активные члены (.a=0 vs .b=0), поэтому шаблонные аргументы считаются разными.