fork download
  1. #include <iostream>
  2. #include <type_traits>
  3.  
  4. template< typename T, T... VALUES > struct seq_c { using value_type = T ; };
  5.  
  6. template< typename T, T... > struct size ;
  7. template< typename T, T... VALUES > struct size< seq_c< T, VALUES...> >
  8. { static constexpr std::size_t value = sizeof...(VALUES) ; } ;
  9.  
  10. template< typename T > struct pop_front {} ;
  11. template< typename T, T V, T... VALUES > struct pop_front< seq_c< T, V, VALUES...> >
  12. { using type = seq_c< T, VALUES...> ; } ;
  13.  
  14. template< std::size_t N, typename T > struct at {} ;
  15. template< std::size_t N, typename T, T V, T... VALUES > struct at< N, seq_c< T, V, VALUES...> >
  16. { static constexpr T value = at<N-1, typename pop_front< seq_c< T, V, VALUES...> >::type >::value ; } ;
  17. template< typename T, T V, T... VALUES > struct at< 0, seq_c< T, V, VALUES...> >
  18. { static constexpr T value = V ; } ;
  19. template< typename T > struct front
  20. { static constexpr typename T::value_type value = at<0,T>::value ; } ;
  21.  
  22. template< typename T, T V, typename U > struct push_back {} ;
  23. template< typename T, T V > struct push_back< T, V, seq_c<T> >
  24. { using type = seq_c<T,V> ; } ;
  25. template< typename T, T V, T... VALUES > struct push_back< T, V, seq_c< T, VALUES...> >
  26. { using type = seq_c< T, VALUES..., V > ; } ;
  27.  
  28. template < typename T, typename U, std::size_t N = size<T>::value > struct paiwise_sum
  29. {
  30. using common_type = typename std::common_type< typename T::value_type,
  31. typename U::value_type >::type ;
  32. using type = typename push_back<
  33. common_type,
  34. front<T>::value + front<U>::value,
  35. typename paiwise_sum< typename pop_front<T>::type,
  36. typename pop_front<U>::type >::type >::type ;
  37. };
  38. template < typename T, typename U > struct paiwise_sum<T,U,0>
  39. {
  40. using type = seq_c< typename std::common_type< typename T::value_type,
  41. typename U::value_type >::type > ; };
  42.  
  43. template < typename T, T A, T B > struct max
  44. { static constexpr T value = A < B ? B : A ; } ;
  45. template< typename T > struct max_element {};
  46. template< typename T, T V, T... VALUES > struct max_element< seq_c< T, V, VALUES...> >
  47. {
  48. using value_type = typename seq_c< T, V, VALUES...>::value_type ;
  49. static constexpr T value = max< T, V, max_element< seq_c< T, VALUES...> >::value >::value ;
  50. } ;
  51. template< typename T, T V > struct max_element< seq_c< T, V > > { static constexpr T value = V ; } ;
  52.  
  53. template < typename T > struct print {} ;
  54. template < typename T > struct print< seq_c<T> > {};
  55. template< typename T, T V, T... VALUES >
  56. struct print< seq_c< T, V, VALUES...> > : print< seq_c<T,VALUES...> >
  57. { print() { std::cout << V << ' ' ; } } ;
  58.  
  59. int main()
  60. {
  61. using a = seq_c< long long , 10, 20, 30, 40, 50 > ;
  62. using b = seq_c< int, -1, -17, -23, 0, -45 > ;
  63. using c = paiwise_sum<a,b>::type ;
  64. print<c>{} ;
  65. std::cout << " max: " << max_element<c>::value << '\n' ;
  66. }
  67.  
Success #stdin #stdout 0s 2896KB
stdin
Standard input is empty
stdout
9 3 7 40 5   max: 40