add utils::type_family

This commit is contained in:
2019-04-18 00:23:05 +07:00
parent 48d9977e16
commit c6c20df1a6
2 changed files with 43 additions and 4 deletions

View File

@@ -147,4 +147,36 @@ namespace e2d { namespace utils
constexpr std::underlying_type_t<E> enum_to_underlying(E e) noexcept {
return static_cast<std::underlying_type_t<E>>(e);
}
//
// type_family
//
using type_family_id = u32;
namespace impl
{
template < typename Void = void >
class type_family_base {
static_assert(
std::is_void<Void>::value &&
std::is_unsigned<type_family_id>::value,
"unexpected internal error");
protected:
static type_family_id last_id_;
};
template < typename Void >
type_family_id type_family_base<Void>::last_id_ = 0u;
}
template < typename T >
class type_family final : public impl::type_family_base<> {
public:
static type_family_id id() noexcept {
static type_family_id self_id = ++last_id_;
assert(self_id > 0u && "type_family_id overflow");
return self_id;
}
};
}}

View File

@@ -49,4 +49,11 @@ TEST_CASE("utils") {
42u, str1, str1 + std::strlen(str1)
) == utils::sdbm_hash(42u, str2));
}
{
utils::type_family_id id1 = utils::type_family<str16>::id();
utils::type_family_id id2 = utils::type_family<str32>::id();
REQUIRE(id1 != id2);
REQUIRE(id1 == utils::type_family<str16>::id());
REQUIRE(id2 == utils::type_family<str32>::id());
}
}