Can I use decltype (or something similar) for explicit template instantiation without signature duplication?

ぐ巨炮叔叔 提交于 2019-12-06 06:57:34

问题


I want to instantiate

template<typename T> void foo(
    T& t,
    SomeType some_parameter,
    AnotherType another_parameter,
    EtcType yet_another_parameter,
    AsYouCanTell this_is_a_very_long_signature);

that is, a function with a long signature. Now, I know how to do this:

template void foo<int>(
    int& t,
    SomeType some_parameter,
    AnotherType another_parameter,
    EtcType yet_another_parameter,
    AsYouCanTell this_is_a_very_long_signature);

But I have to duplicate the signature. Also, what if want specific instantiation for 5 different types - do I copy it 5 times? Doesn't make sense...

I was thinking maybe I could write

template decltype(foo<int>);

but for some reason this doesn't work. Why?


回答1:


It actually works but the syntax is different:

template
decltype(foo<int>) foo<int>;

decltype gives you a type but the explicit instantiation requires a declaration which is a type followed by a name.

Tried with GCC 4.9.1; it works as expected and compiles without any warnings even with the -pedantic flag.




回答2:


It's actually even simpler than @5gon12eder suggested:

template decltype(foo<int>) foo;

but yes, it's just like he said - decltype() only provides the type, and a signature is not really a type.

Edit: This doesn't work when the template has value arguments rather than just types, so if we have

template <typename T, unsigned Val> bar(T t);

then

template decltype(bar<int, 1>) bar;

will not compile, while

template decltype(bar<int, 1>) bar<int, 1>;

will.




回答3:


No, because of overloading

template<typename T> void foo(T& t,
                     SomeType some_parameter,
                     AnotherType another_parameter,
                     EtcType yet_another_parameter,
                     AsYouCanTell this_is_a_very_long_signature);
template<template T> void foo(T& t); //completely unrelated function
template<template T> void foo(char); //another completely unrelated function

Now imagine, what is the minimum information required to explicitly instantiate the first one? Well, you need the full signature to disambiguate it, so

explicit int foo(int&, SomeType, AnotherType, EtcType, AsYouCanTell)

is the theoretical minimum amount of information. So what C++ requires actually has very little overhead:

template void foo<int>(int& t, SomeType, AnotherType, EtcType, AsYouCanTell);

If you don't want to type all that, then Konrad's suggestion of a macro is the way to go.




回答4:


I think this is a good, legitimate use for a macro:

#define INSTANTIATE_FOO(type) \
    template void foo<type>(type& t, \
                  SomeType some_parameter, \
                  AnotherType another_parameter, \
                  EtcType yet_another_parameter, \
                  AsYouCanTell this_is_a_very_long_signature);

INSTANTIATE_FOO(int)
INSTANTIATE_FOO(float)
INSTANTIATE_FOO(my_little_dragon)

#undef INSTANTIATE_FOO


来源:https://stackoverflow.com/questions/28355934/can-i-use-decltype-or-something-similar-for-explicit-template-instantiation-wi

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!