Как я могу получить ту же обработку приведения типов для пользовательских типов, что и встроенную, например:
float a = 5.4;
std::string s = a;//error, no conversion avaible
int x = a;//warning, possible data loss
int y = (int)a;//fine
int z = static_cast<int>a;//fine
float b = c;//warning, possible data loss
Теперь скажите, что у меня есть свои собственные классы Int и Float, как мне получить те же ошибки и предупреждения?
class Int
{
public:
int value;
Int(int v);
...
};
class Float
{
public:
float value;
Float(float v);
...
};
Int c = 10;
Float a = 5.5;
std::string s = a;
Int x = a;
Int y = (Int)a;
Int z = static_cast<Int>a;
Float b = c;
Мне известно о создании перегруженных операторов приведения и использовании конструкторов, однако я не знаю, как заставить это работать правильно для неявных и явных приведений, например, рассмотреть. Если я не добавляю явные приведения в эти методы, тогда я получаю предупреждение, когда они скомпилированы, но не при их вызове, и если я это делаю, то я не получаю сообщение об ошибке в коде классов, но все равно не получаю предупреждение при использовании либо.
Я предполагаю, что есть какой-то способ пометить оператор приведения как явный, чтобы генерировалось предупреждение, если он пытается привести неявно, но не с явным (C-Style или static_cast) приведением)
EDIT:
Хорошо, я думаю, что получаю это для случаев, подобных этому, когда все рассматриваемые типы полностью известны, но как насчет случаев, когда один или оба являются шаблонами, и что ни один из типов не отображается на встроенный тип?
template<typename T> class Vector2
{
public:
T x, y;
Vector2():x(0),y(0){}
Vector2(T x, T y):x(x),y(y){}
//Works as expected, warning if adding T and T2 is unsafe, or error if
//incompatible*/
template<typename T2>Vector2<T>& operator += (const Vector2<T2> &v);
//Also works as desired
Vector2<T>& operator *= (T s);
//allows the conversion, but always generates warnings if
//T and T2 would, even if this constructor is used by an explicit
//case. How can I suppress the warnings for the explicit cast, but
//not for implicit casts?
template<typename T2>Vector2(const Vector2<T2> &v);//uses implicit conversion form T2 to T
};
Неявное приведение из, скажем, Vector2 к Vector2 работает, как и ожидалось, но приведение из, скажем, Vector2 к Vector2 всегда вызывает (2, один для x и один для y) предупреждения, даже если использовался явный C-Style или static_cast. Я хочу сохранить предупреждения для неявных приведений, но не для явных приведений.
Я знаю, что могу взломать это, создав специальный метод типа T vector_cast (T2), который использует явное приведение для каждого элемента внутри, но я бы предпочел использовать C-Style и static_casts