Imported Upstream version 16.3.2
[platform/upstream/libzypp.git] / zypp / base / TypeTraits.h
1 /*---------------------------------------------------------------------\
2 |                          ____ _   __ __ ___                          |
3 |                         |__  / \ / / . \ . \                         |
4 |                           / / \ V /|  _/  _/                         |
5 |                          / /__ | | | | | |                           |
6 |                         /_____||_| |_| |_|                           |
7 |                                                                      |
8 \---------------------------------------------------------------------*/
9 /** \file       zypp/base/TypeTraits.h
10  */
11 #ifndef ZYPP_TYPETRAITS_H
12 #define ZYPP_TYPETRAITS_H
13
14 #include <type_traits>
15
16 ///////////////////////////////////////////////////////////////////
17 namespace zypp
18 {
19   ///////////////////////////////////////////////////////////////////
20   namespace _detail
21   {
22     template<typename Tp>
23     struct _has_type_const_iterator
24     {
25     private:
26       template<typename C> static std::true_type  test( typename C::const_iterator * );
27       template<typename C> static std::false_type test(...);
28     public:
29       static constexpr bool value = decltype(test<Tp>(nullptr))::value;
30     };
31
32     template <typename Tp>
33     struct _has_container_begin_end
34     {
35     private:
36       template <typename C>
37       using Signature = typename C::const_iterator(C::*)() const;
38
39       template<typename C> static std::true_type  testBeg( typename std::enable_if<std::is_same<decltype(static_cast<Signature<C>>(&C::begin)), Signature<C>>::value, void>::type* );
40       template<typename C> static std::false_type testBeg(...);
41
42       template<typename C> static std::true_type  testEnd( typename std::enable_if<std::is_same<decltype(static_cast<Signature<C>>(&C::end)), Signature<C>>::value,   void>::type* );
43       template<typename C> static std::false_type testEnd(...);
44
45     public:
46       static constexpr bool beg_value = decltype(testBeg<Tp>(nullptr))::value;
47       static constexpr bool end_value = decltype(testEnd<Tp>(nullptr))::value;
48       static constexpr bool value = beg_value && end_value;
49     };
50   } // namespace _detail
51   ///////////////////////////////////////////////////////////////////
52
53   /** Whether \a Tp defines type \a Tp::const_iterator */
54   template<typename Tp>
55   struct has_type_const_iterator
56   : public std::integral_constant<bool, _detail::has_type_const_iterator<Tp>::value>
57   {};
58
59   /** Whether \a Tp defines methods <tt>Tp::const_iterator begin/end() const</tt> */
60   template<typename Tp>
61   struct has_container_begin_end
62   : public std::integral_constant<bool, _detail::_has_container_begin_end<Tp>::value>
63   {};
64
65   /** Whether \a Tp is a container (begin/end iterabel, but not plain std::string) */
66   template<typename Tp>
67   struct is_container
68   : public std::integral_constant<bool, !std::is_same<Tp, std::string>::value && has_container_begin_end<Tp>::value>
69   {};
70
71
72 } // namespace zypp
73 ///////////////////////////////////////////////////////////////////
74 #endif // ZYPP_TYPETRAITS_H