class Parent {};
class Child : public Parent {};
class Foo
{
public:
Foo (Parent &) {};
template <typename T>
Foo (const T &);
};
int main ()
{
Child c;
Foo foo (c);
}
This produces a linker error since the constructor for foo chooses template<typename T>Foo::Foo(const T &) instead of Foo::Foo(Parent&).
If c has type Parent instead of Child, this uses the non-template constructor and links with no issues.
I can work around this with
Foo foo ((Parent&) c);
but I don't want to do that.
Why does C++ prefer to use a template instead of implicitly casting c to Parent&?
Can I change the class to prefer casting to templating, so the workaround is not needed?
The compiler prefers to choose the template constructor with
T=childbecause overload resolution considers that a qualification conversion (addingconstto the argument type) is better than a derived to base conversion.So the simplest way is just to declare a constructor taking a child as argument:
Notice that if the argument to the constructor is a const lvalue or an rvalue, then as in your example code the template constructor will be selected. I suppose that this is intentional.