Reputation: 1228
I have a some classes with a function. In all classes the function has the same name and argument type but different return type. I need a some template function which can automagically detect correct template substitution without angle brackets.
Test code to illustrate question:
struct Float
{
static Float convert(int i)
{
return Float{static_cast<float>(i)};
}
float _f;
};
struct Int
{
static Int convert(int i)
{
return Int{i};
}
int _i;
};
template<typename T>
T convert(int i)
{
return T::convert(i);
}
int main()
{
Float f1 = convert<Float>(10);
Int i1 = convert<Int>(10);
// Float f2 = convert(10); compilation error
// Int i2 = convert(10); compilation error
return 0;
}
P.S. templates makes me crazy I want but can't understand them.
Upvotes: 1
Views: 108
Reputation:
Why do you need the convert function? You can use a single argument constructor to do the same job.
struct Float
{
Float(int i)
{
_f = static_cast<float>(i);
}
float _f;
};
struct Int
{
Int(int i)
{
_i = static_cast<int>(i);
}
int _i;
};
int main()
{
Float f2 = 10;
Int i2 = 10;
return 0;
}
If you're worried about the implicit calls to the constructor you can make it explicit
struct Float
{
explicit Float(int i)
{
_f = static_cast<float>(i);
}
float _f;
};
int main()
{
Float f2 = Float(10);
return 0;
}
The readability of the code is affected if the function with same name and the same type of input arguments can produce different return types.
Upvotes: 0
Reputation: 170065
Not sure if it's a perfect fit to your needs, but you may simulate what you want with a class and a templated conversion operator:
class convert {
int arg;
public:
convert(int arg) : arg(arg) {}
template<class T>
operator T() const {
return T::convert(arg);
}
};
Since template argument deduction works for templated conversion operators, you can write this:
Float f1 = convert(10);
Int i1 = convert(10);
Just like you want.
Upvotes: 7