Я хотел как-то расширить тип Microsoft _variant_t
, чтобы он принимал неявные / явные преобразования в / из дополнительных типов.Для этого я написал следующий класс:
class value_type
{
public:
/* Constructors */
value_type(const std::string& str) : m_variant(str.c_str()) {}
template <typename Type> value_type(const Type& value) : m_variant(value) {}
/* Conversion operators */
operator const _variant_t&() const { return m_variant; }
operator std::string() const { return static_cast<const char*>(m_variant); }
template <typename Type> operator Type() const { return static_cast<Type>(m_variant); }
private:
_variant_t m_variant;
};
То есть, если каждый экземпляр _variant_t
в коде заменяется на value_type
, он "работает" то же самое.
Давайте рассмотрим следующую функцию, которая возвращает _variant_t
:
_variant_t foo();
Если я напишу:
std::string bar()
{
value_type v = foo();
return v;
}
Он прекрасно компилируется.
Но если я изменю предыдущий код следующим образом:
std::string bar()
{
return value_type(foo());
}
или:
std::string bar()
{
return static_cast<std::string>(value_type(foo()));
}
Компиляция завершится неудачно со следующим сообщением:
configuration.cpp (41): ошибка C2668: 'std :: basic_string <_Elem, _Traits, _Ax> :: basic_string': неоднозначный вызов перегруженной функции
Если удалить строку template <typename Type> operator Type...
все компилируется.
Теперь я понимаю, что говорит компилятор (он не знает, какой оператор использовать), но я не понимаю, почему: Казалось бы логично использовать operator std::string
при преобразовании в std::string
.Чего мне не хватает?
Спасибо.