10 #ifndef SRC_INCLUDE_SMASH_TRAITS_H_
11 #define SRC_INCLUDE_SMASH_TRAITS_H_
18 #include <type_traits>
57 template <
typename... Args>
65 template <
typename... Args>
73 template <
typename... Args>
88 : std::bool_constant<detail::is_stl_container<std::decay_t<T>>::value> {};
104 template <
typename T,
typename Enable =
void>
114 template <
typename T>
121 template <
typename T>
132 template <
typename T>
142 template <
typename K,
typename V,
typename... Args>
148 template <
typename T>
160 template <
typename S,
typename T,
typename Enable =
void>
169 template <
typename S,
typename T>
171 S, T, std::void_t<decltype(std::declval<S&>() << std::declval<T>())>>
177 template <typename S, typename T>
178 inline constexpr bool is_streamable_v = is_streamable<S, T>::value;
191 template <typename S, typename T, typename Enable = void>
192 struct is_writable_to_stream : std::false_type {};
207 template <typename S, typename T>
208 struct is_writable_to_stream<
209 S, T, std::enable_if_t<!is_stl_container_v<T> && !is_tuple_like_v<T>>>
210 : std::bool_constant<is_streamable_v<S, T>> {};
226 template <typename S, typename T>
227 struct is_writable_to_stream<
228 S, T, std::enable_if_t<is_stl_container_v<T> && !is_map_like_v<T>>>
229 : std::bool_constant<
230 is_streamable_v<S, T> &&
231 is_writable_to_stream<S, typename T::value_type>::value> {};
245 template <typename S, typename T>
246 struct is_writable_to_stream<S, T, std::enable_if_t<is_map_like_v<T>>> {
249 using key_type = typename T::key_type;
251 using mapped_type = typename T::mapped_type;
255 static constexpr bool value = is_streamable_v<S, T> &&
256 is_writable_to_stream<S, key_type>::value &&
257 is_writable_to_stream<S, mapped_type>::value;
272 template <typename S, typename T>
273 struct is_writable_to_stream<S, T, std::enable_if_t<is_tuple_like_v<T>>> {
284 template <std::size_t... I>
285 static constexpr bool check(std::index_sequence<I...>) {
286 return (is_writable_to_stream<S, std::tuple_element_t<I, T>>::value && ...);
291 static constexpr bool value =
292 is_streamable_v<S, T> &&
293 check(std::make_index_sequence<std::tuple_size_v<T>>{});
299 template <typename S, typename T>
300 inline constexpr bool is_writable_to_stream_v =
301 is_writable_to_stream<S, T>::value;
311 template <typename T, typename Enable = void>
312 struct has_to_string : std::false_type {};
330 template <typename T>
331 struct has_to_string<T,
332 std::void_t<decltype(smash::to_string(std::declval<T>()))>>
333 : std::is_same<decltype(smash::to_string(std::declval<T>())), std::string> {
345 template <std::size_t N>
346 struct has_to_string<std::bitset<N>, std::void_t<decltype(smash::to_string(
347 std::declval<std::bitset<N>>()))>>
348 : std::is_same<decltype(smash::to_string(std::declval<std::bitset<N>>())),
349 std::vector<std::string>> {};
354 template <typename T>
355 inline constexpr bool has_to_string_v = has_to_string<T>::value;
constexpr bool is_tuple_like_v
Helper alias which is common to be defined next to a type trait.
constexpr bool is_map_like_v
Helper alias which is common to be defined next to a type trait.
constexpr bool is_stl_container_v
Helper alias which is common to be defined next to a type trait.
static const uint32_t K[64]
The K array.
Implementation of the type trait to infer if a type is an STL container.
Type trait to infer if a type is map-like (for the moment only std::map is considered).
Type trait to infer if a type is an STL container.
Type trait to infer if a type can be streamed via the << operator.
Type trait to infer if a type is tuple-like (std::pair or std::tuple or std::array or few others).