#include <iostream>
#include <type_traits>
#include <tuple>
struct fizz{ static char const value[ ]; };
char const fizz::value[ ] = "fizz";
struct buzz{ static char const value[ ]; };
char const buzz::value[ ] = "buzz";
struct fizzbuzz{ static char const value[ ]; };
char const fizzbuzz::value[ ] = "fizzbuzz";
template< std::size_t I >
struct num{ static std::size_t const value = I; };
template< std::size_t I >
using fizzbuzz_val = std::conditional< I % 15 == 0, fizzbuzz,
typename std::conditional< I % 3 == 0, fizz,
typename std::conditional< I % 5 == 0, buzz,
num<I>
>::type
>::type
>;
template< class T, class U>
struct append;
template< class... Args, class T >
struct append< std::tuple<Args...>, T >{
typedef std::tuple< Args..., T > type;
};
template< std::size_t I >
struct fizzbuzz_seq{
typedef typename append< typename fizzbuzz_seq<I-1>::type,
typename fizzbuzz_val<I>::type
>::type type;
};
template<>
struct fizzbuzz_seq<1>{
typedef std::tuple<num<1>> type;
};
template< class T >
struct print_tuple_values;
template< class T, class... Args >
struct print_tuple_values<std::tuple<T, Args...>>{
void operator()() const
{
std::cout << T::value << '\n';
print_tuple_values<std::tuple<Args...>>()();
}
};
template< class T >
struct print_tuple_values<std::tuple<T>>{
void operator()() const
{
std::cout << T::value << '\n';
}
};
int main()
{
typedef typename fizzbuzz_seq<100>::type result;
print_tuple_values<result>()();
return 0;
}