fork download
  1. #include <iostream>
  2. #include <type_traits>
  3.  
  4. template <int I> using int_ = std::integral_constant<int, I>;
  5.  
  6. template<typename T> using eval = typename T::type;
  7.  
  8. template<typename... List>
  9. struct seq
  10. {
  11. using type = seq;
  12. };
  13.  
  14. template<typename> struct car;
  15. template<typename Car, typename... Cdr>
  16. struct car< seq<Car, Cdr...>>
  17. {
  18. typedef Car type;
  19. };
  20.  
  21. template<typename> struct cdr;
  22. template<typename Car, typename... Cdr>
  23. struct cdr< seq<Car, Cdr...>>
  24. {
  25. typedef seq<Cdr...> type;
  26. };
  27.  
  28.  
  29. template <typename, typename> struct cons;
  30. template <typename T, typename... L>
  31. struct cons<T, seq<L...>>
  32. {
  33. typedef seq<T, L...> type;
  34. };
  35.  
  36. template<typename, typename> struct concat;
  37. template <typename... As, typename... Bs>
  38. struct concat<seq<As...>, seq<Bs...>>
  39. {
  40. typedef seq<As..., Bs...> type;
  41. };
  42.  
  43. template<typename> struct length;
  44. template<typename... As>
  45. struct length<seq<As...>>
  46. {
  47. typedef std::integral_constant<unsigned, sizeof...(As)> type;
  48. };
  49.  
  50. template<typename>
  51. struct is_empty
  52. {
  53. typedef std::integral_constant<bool, true> type;
  54. };
  55.  
  56. template<>
  57. struct is_empty<seq<>>
  58. {
  59. typedef std::integral_constant<bool, true> type;
  60. };
  61.  
  62. template<template<typename... Args> class Fun, typename... Args>
  63. struct apply
  64. {
  65. typedef eval<Fun<Args...>> type;
  66. };
  67.  
  68. typedef seq<int_<1>, int_<2>, int_<3> > s1;
  69. typedef seq<int_<7>, int_<5>, int_<9> > s2;
  70. typedef seq<int_<1>, s2, int_<17>, s1 > s3;
  71. typedef seq<> empty;
  72. template<typename Seq> using concat_fix = apply<concat, s2, Seq>;
  73.  
  74. int main()
  75. {
  76.  
  77. std::cerr << eval < length < eval < apply < concat, s1, s3 >> >> ::value << '\n';
  78. std::cerr << eval < length <eval< concat_fix<s3>>>>::value << '\n';
  79. std::cerr << eval < apply < length, empty> >::value << '\n';
  80. std::cerr << eval<length < eval < concat<s1, s3 >>>>::value << '\n';
  81. return 0;
  82. }
Success #stdin #stdout #stderr 0s 3292KB
stdin
Standard input is empty
stdout
Standard output is empty
stderr
7
7
0
7