I am studying operator overloading, there are some parts that are difficult to understand.
See this example code.
class A {
private:
char a;
int b;
double c;
public:
A(char _a = 'a', int _b = 99, double _c = 1.618) :a(_a), b(_b), c(_c){
}
public:
operator char() const {
cout << "operator char() called" << endl;
return this->a;
}
operator int() const {
cout << "operator int() called" << endl;
return this->b;
}
operator double() {
cout << "operator double() called" << endl;
return this->c;
}
};
int main(void) {
A a;
char b = a;
int c = a;
double d = a;
printf("%c\n", b);
printf("%d\n", c);
printf("%f\n", d);
return 0;
}
I made this code to test for type conversion operator and expected that the appropriate function would be called for each type of data.
But the result is..
operator double() called
operator double() called
operator double() called
<-- strange character is gone on board!
1
1.618000
I can not understand why the results are not as follows.
operator char() called
operator int() called
operator double() called
a
99
1.618
Why is double operator called when converting to char and int?
Have a good day! :)
In this article we will see what is the conversion operator in C++. C++ supports object oriented design. So we can create classes of some real world objects as concrete types. Sometimes we need to convert some concrete type objects to some other type objects or some primitive datatypes.
Explicit Type Conversion– This process is also called type casting and it is user defined. Here the user can type cast the result to make it of a particular data type. The syntax in C: (type) expression Type indicated the data type to which the final result is converted.
Conversion constructors define conversions from user-defined or built-in types to a user-defined type. The following example demonstrates a conversion constructor that converts from the built-in type double to a user-defined type Money.
User-defined conversion operators (C# reference) A user-defined type can define a custom implicit or explicit conversion from or to another type. Implicit conversions don't require special syntax to be invoked and can occur in a variety of situations, for example, in assignments and methods invocations.
You forgot the const
on the double
conversion operator:
operator double() const { // <---------------------------
cout << "operator double() called" << endl;
return this->c;
}
};
As in your example a
is not const
, the double conversion is the best match. If you fix that you get the expected output.
Live example
...some opinion based PS:
I didnt find what the core guidelines say about conversion operators, but if I had to make up a guideline for conversion operators it would be: Avoid them. If you use them, make them explicit
. The surprising effects of implicit conversion outweigh the benefits by far.
Just as an example, consider std::bitset
. Instead of offering conversion operators it has to_string
, to_ulong
and to_ullong
. It is better to have your code explicit. A a; double d = a;
is a little bit mysterious. I would have to look at the class definition to get an idea of what is really going on. On the other hand A a; double d = a.as_double();
can do the exact same thing, but is way more expressive.
Yea so the problem is, that you made all operators const except for the double operator. I am still a bit surprised because this const just means that the operator call does not modify the class members. Still it seems that only the double operator is called for all 3. I would all 3 op's make const and then it will work properly.
If someone has an explanation why this happens, I would also like to know. Cheers.
operator char() const { // here is const
cout << "operator char() called" << endl;
return this->a;
}
operator int() const { // here is const
cout << "operator int() called" << endl;
return this->b;
}
operator double() { // here is no const
cout << "operator double() called" << endl;
return this->c;
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With