Недавно, я просматривал свою копию Ссылки Кармана C++ от O'Reilly Media, и я был удивлен, когда я столкнулся с кратким разделом и примером относительно пользовательского преобразования для пользовательских типов:
#include <iostream>
class account {
private:
double balance;
public:
account (double b) { balance = b; }
operator double (void) { return balance; }
};
int main (void) {
account acc(100.0);
double balance = acc;
std::cout << balance << std::endl;
return 0;
}
Я программировал в C++ некоторое время, и это - первый раз, когда я когда-либо видел этот вид перегрузки оператора. Описание книги этого предмета несколько кратко, оставляя меня с несколькими оставшимися без ответа вопросами об этой функции:
Могут пользовательские преобразования в определяемые пользователем типы быть сделанными? например.
станд. оператора:: строка () {/* кодирует */}
Это особенно непонятная функция?
Да, операторы преобразования используются не очень часто. Я встречал их только для пользовательских типов, которые могут вырождаться до встроенных. Например, класс чисел фиксированной точности, который поддерживает преобразование в/из атомарных типов чисел.
Это относительно переносимо?
Насколько я знаю, да. Они были в стандарте всегда.
Можно ли выполнять преобразования к типам, определенным пользователем?
Да, это одна из особенностей конструкторов. Конструктор, принимающий один аргумент, фактически создает оператор преобразования от типа аргумента к типу вашего класса. Например, класс типа this:
class Foo {
public:
Foo(int n) {
// do stuff...
}
}
Позволяет вам делать:
Foo f = 123;
Если вы уже использовали std::string
, то, скорее всего, вы использовали эту возможность, не осознавая этого. (В качестве примера, если вы хотите предотвратить такое поведение, объявляйте любые одноаргументные конструкторы с помощью explicit
.)
Это было примерно одно из первых, на что я наткнулся, когда изучал C ++, поэтому я бы сказал, что нет, это не так уж и непонятно.
Однако я хотел бы предупредить об одном: используйте с ними ключевое слово explicit
, если вы точно не знаете, что делаете. Неявные преобразования могут привести к неожиданному поведению кода, поэтому в большинстве случаев их следует избегать. Честно говоря, я был бы счастлив, если бы их не было в языке.
Это не особенно непонятно; это очень переносимо (в конце концов, это часть языка), и возможно преобразование в пользовательские типы.
Одно слово предостережения: наличие большого количества возможных неявных путей преобразования может привести к неожиданному вызову преобразования и неожиданным ошибкам. Кроме того, наличие неявных конструкторов преобразования и функций преобразования между несколькими определяемыми пользователем типами может привести к более неоднозначным ситуациям преобразования, которые будет очень сложно разрешить.
Это особенно полезная стандартная функция C++ и не такая уж и непонятная :) Вы можете использовать для операторов преобразования как фундаментальные, так и определяемые пользователем типы.