10
10
#define _LIBCPP___TYPE_TRAITS_CONJUNCTION_H
11
11
12
12
#include < __config>
13
- #include < __type_traits/conditional.h>
14
- #include < __type_traits/enable_if.h>
15
13
#include < __type_traits/integral_constant.h>
16
14
#include < __type_traits/is_same.h>
17
15
21
19
22
20
_LIBCPP_BEGIN_NAMESPACE_STD
23
21
24
- template <class ... >
25
- using __expand_to_true _LIBCPP_NODEBUG = true_type ;
22
+ template <bool >
23
+ struct _AndImpl ;
26
24
27
- template <class ... _Pred>
28
- __expand_to_true<__enable_if_t <_Pred::value>...> __and_helper (int );
25
+ template <>
26
+ struct _AndImpl <true > {
27
+ template <class _Res , class _First , class ... _Rest>
28
+ using _Result _LIBCPP_NODEBUG =
29
+ typename _AndImpl<bool (_First::value) && sizeof ...(_Rest) != 0 >::template _Result<_First, _Rest...>;
30
+ };
29
31
30
- template <class ...>
31
- false_type __and_helper (...);
32
+ template <>
33
+ struct _AndImpl <false > {
34
+ template <class _Res , class ...>
35
+ using _Result _LIBCPP_NODEBUG = _Res;
36
+ };
32
37
33
38
// _And always performs lazy evaluation of its arguments.
34
39
//
35
40
// However, `_And<_Pred...>` itself will evaluate its result immediately (without having to
36
41
// be instantiated) since it is an alias, unlike `conjunction<_Pred...>`, which is a struct.
37
42
// If you want to defer the evaluation of `_And<_Pred...>` itself, use `_Lazy<_And, _Pred...>`.
38
- template <class ... _Pred >
39
- using _And _LIBCPP_NODEBUG = decltype(std::__and_helper<_Pred ...>( 0 )) ;
43
+ template <class ... _Args >
44
+ using _And _LIBCPP_NODEBUG = typename _AndImpl< sizeof ...(_Args) != 0 >:: template _Result<true_type, _Args ...>;
40
45
41
46
template <bool ... _Preds>
42
47
struct __all_dummy ;
@@ -46,22 +51,11 @@ struct __all : _IsSame<__all_dummy<_Pred...>, __all_dummy<((void)_Pred, true)...
46
51
47
52
#if _LIBCPP_STD_VER >= 17
48
53
49
- template <class ...>
50
- struct _LIBCPP_NO_SPECIALIZATIONS conjunction : true_type {};
51
-
52
- _LIBCPP_DIAGNOSTIC_PUSH
53
- # if __has_warning("-Winvalid-specialization")
54
- _LIBCPP_CLANG_DIAGNOSTIC_IGNORED (" -Winvalid-specialization" )
55
- # endif
56
- template <class _Arg >
57
- struct conjunction <_Arg> : _Arg {};
58
-
59
- template <class _Arg , class ... _Args>
60
- struct conjunction <_Arg, _Args...> : conditional_t <!bool (_Arg::value), _Arg, conjunction<_Args...>> {};
61
- _LIBCPP_DIAGNOSTIC_POP
54
+ template <class ... _Args>
55
+ struct _LIBCPP_NO_SPECIALIZATIONS conjunction : _And<_Args...> {};
62
56
63
57
template <class ... _Args>
64
- _LIBCPP_NO_SPECIALIZATIONS inline constexpr bool conjunction_v = conjunction <_Args...>::value;
58
+ _LIBCPP_NO_SPECIALIZATIONS inline constexpr bool conjunction_v = _And <_Args...>::value;
65
59
66
60
#endif // _LIBCPP_STD_VER >= 17
67
61
0 commit comments