Skip to content

Instantly share code, notes, and snippets.

@ericniebler
Created April 12, 2017 16:09
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ericniebler/6612dd73d8eb1d7168a97f8f4927393d to your computer and use it in GitHub Desktop.
Save ericniebler/6612dd73d8eb1d7168a97f8f4927393d to your computer and use it in GitHub Desktop.
#include <type_traits>
template<int I> struct priority_tag : priority_tag<I - 1> {};
template<> struct priority_tag<0> {};
// Function types here:
template<typename T>
char (&is_function_impl_(priority_tag<0>))[1];
// Array types here:
template<typename T, typename = decltype((*(T*)0)[0])>
char (&is_function_impl_(priority_tag<1>))[2];
// Anything that can be returned from a function here (including
// void and reference types):
template<typename T, typename = T(*)()>
char (&is_function_impl_(priority_tag<2>))[3];
// Classes and unions (including abstract types) here:
template<typename T, typename = int T::*>
char (&is_function_impl_(priority_tag<3>))[4];
template <typename T>
struct is_function
: std::integral_constant<bool, sizeof(is_function_impl_<T>(priority_tag<3>{})) == 1>
{};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment