65 lines
2 KiB
C++
65 lines
2 KiB
C++
#pragma once
|
|
|
|
#include <utility>
|
|
|
|
namespace util {
|
|
|
|
template <typename T1, typename T2>
|
|
struct copy_const : std::type_identity<T2> {};
|
|
|
|
template <typename T1, typename T2>
|
|
struct copy_const<const T1, T2> : std::type_identity<const T2> {};
|
|
|
|
template <typename T1, typename T2>
|
|
using copy_const_t = typename copy_const<T1, T2>::type;
|
|
|
|
template <typename T1, typename T2>
|
|
struct copy_volatile : std::type_identity<T2> {};
|
|
|
|
template <typename T1, typename T2>
|
|
struct copy_volatile<volatile T1, T2> : std::type_identity<volatile T2> {};
|
|
|
|
template <typename T1, typename T2>
|
|
using copy_volatile_t = typename copy_volatile<T1, T2>::type;
|
|
|
|
template <typename T1, typename T2>
|
|
struct copy_cv : std::type_identity<copy_const_t<T1, copy_volatile_t<T1, T2>>> {
|
|
};
|
|
|
|
template <typename T1, typename T2>
|
|
using copy_cv_t = typename copy_cv<T1, T2>::type;
|
|
|
|
template <typename T1, typename T2>
|
|
struct copy_reference : std::type_identity<T2> {};
|
|
template <typename T1, typename T2>
|
|
struct copy_reference<T1 &, T2>
|
|
: std::type_identity<std::add_lvalue_reference_t<T2>> {};
|
|
template <typename T1, typename T2>
|
|
struct copy_reference<T1 &&, T2>
|
|
: std::type_identity<std::add_rvalue_reference_t<T2>> {};
|
|
|
|
template <typename T1, typename T2>
|
|
using copy_reference_t = typename copy_reference<T1, T2>::type;
|
|
|
|
template <typename T1, typename T2>
|
|
using copy_cvref_t = copy_reference_t<
|
|
T1, copy_reference_t<T2, copy_cv_t<std::remove_reference_t<T1>, T2>>>;
|
|
|
|
template <typename T2>
|
|
constexpr inline auto transmute(auto &&t1) -> copy_cvref_t<decltype(t1), T2> {
|
|
return std::forward<copy_cvref_t<decltype(t1), T2>>(
|
|
reinterpret_cast<copy_cvref_t<decltype(t1), T2>>(t1));
|
|
}
|
|
|
|
template <typename T2>
|
|
constexpr inline auto transmute(auto &t1) -> copy_cvref_t<decltype(t1), T2> {
|
|
return std::forward<copy_cvref_t<decltype(t1), T2>>(
|
|
reinterpret_cast<copy_cvref_t<decltype(t1), T2>>(t1));
|
|
}
|
|
|
|
template <typename T1, typename T2>
|
|
constexpr inline auto transmute(T1 t1) -> T2 {
|
|
return std::forward<T2>(reinterpret_cast<T2>(t1));
|
|
}
|
|
|
|
} // namespace util
|