0

In the following code uses the type inference rules for template parameters (this question is about C++14):

#include <iostream>    

template <typename T>
void test(T x)
{
        std::cout << "T x" << std::endl;
}

template <>
void test<int>(int x)
{
        std::cout << "int x" << std::endl;
}

template <>
void test<int &>(int &x)
{
        std::cout << "int &x" << std::endl;
}

int main()
{
        int x = 5;
        int &y = x;

        test(x);
        test(y);

        return 0;
}

The rules clearly state that references are discarded (es explained, for example, here), so the output

int x
int x

is very much expected as the best matching overload. However in some cases, an output of

int x
int &x

may be desirable. Is there a way for template argument type deduction to infer what is, intuitively, the exact type of the parameter?

  • what do you mean by "intuitively" in the last sentence? Compilers don't run on intuition – M.M Mar 28 '16 at 23:41
  • I'm not sure exactly what you're asking but maybe [this recent thread](http://stackoverflow.com/questions/36050087/how-to-distiguish-between-an-rvalue-and-rvalue-reference-in-a-function-parameter/) will help – M.M Mar 28 '16 at 23:44

1 Answers1

3

You'd have to pass the decltype of the argument. Use this macro to get over the syntactical hurdles:

namespace detail{
    template <typename T> void test(T){std::cout << "T" << std::endl;}
    template <> void test<>(int){std::cout << "int" << std::endl;}
    template <> void test<>(int&){std::cout << "int&" << std::endl;}
}

#define TEST(x) detail::test<decltype(x)>(x)

Now simply call with the arguments:

TEST(x) // int
TEST(y) // int&
David G
  • 94,763
  • 41
  • 167
  • 253