Say I have a class STest
and I want it to be able to implicitly cast to char const*
but not bool
.
struct STest {
operator char const*() const& { return "abc"; }
operator bool() const& = delete;
};
void bar(bool) {}
void foo(bool) {}
void foo(char const*) {}
This implementation works as expected (error) when calling bar(STest{})
. But it doesn't work for foo(STest{})
because deleted function is also considered in overload resolution and it complains ambiguity. Is there a way to workaround this which means bar(STest{})
raises an error and foo(STest{})
calls foo(char const*)
?
You can use a conversion operator template, and constrain it with SFINAE.
struct STest {
template<typename T, std::enable_if_t<std::is_same<char const*, T>::value, int> = 0>
operator T() const& { return "abc"; }
};
Instead of having two overloads participating and causing an error when the wrong one is chosen, this will instead deduce the target type from context, and will then decide if the overload should be removed from overload resolution at all. With a single overload there won't be ambiguity.