В настоящее время я портирую кучу кода, который ранее был скомпилирован только с Visual Studio 2008.
В этом коде есть такая договоренность:
template <typename T>
T convert( const char * s )
{
// slow catch-all
std::istringstream is( s );
T ret;
is >> ret;
return ret;
}
template <typename T, typename T2>
T convert( T2 * s )
{
return convert<T>( static_cast<const char*>( s ));
}
template <typename T, typename T2>
T convert( T2 s )
{
return T( s );
}
template <>
inline int convert<int>( const char * s )
{
return (int)atoi( s );
}
Как правило, существует множество специализаций шаблонной функции с различными типами возвращаемых значений, которые вызываются следующим образом:
int i = convert<int>( szInt );
Проблема в том, что эти специализации шаблонов приводят к "Неоднозначной специализации шаблонов".
Если бы это было что-то помимо возвращаемого типа, которое отличало бы эти специализации функции, я бы, очевидно, мог просто использовать перегрузки, но это не вариант.
Как мне решить эту проблему, не меняя все места, где вызываются функции преобразования?
Обновление
Я добавил эти две универсальные шаблонные специализации, которые я пропустил в первый раз.
Мне стыдно сказать, я не уверен насчет мотивации для второго, но первый из-за того, что функция convert используется во многих местах, где строковые данные передаются как пустота *.
Сейчас я не могу проверить это в GCC, но подозреваю, что это может быть проблемой.
Обновление 2
Вот полный файл cpp, который будет воспроизводить это.
Если вы удалите обе функции общего назначения, он скомпилируется.
Если вы позволите одному из них остаться, это приведет к неоднозначной ошибке специализации шаблона.
#include <iostream>
#include <sstream>
template <typename T>
T convert( const char * s )
{
// this is a slow slow general purpose catch all, if no specialization is provided
std::istringstream is( s );
T ret;
is >> ret;
return ret;
}
// general purpose 1
template <typename T, typename T2>
T convert( T2 * s )
{
return convert<T>( static_cast<const char*>( s ));
}
// general purpose 2
template <typename T, typename T2>
T convert( T2 s )
{
return T( s );
}
// Type specialized
template <>
inline float convert<float>( const char * s )
{
return (float)atof( s );
}
int main( int argc, const char * sz[] )
{
return 0;
}