#include <iostream>
usingnamespace std;
class test {
private:
int x;
public:
test(constint y) {
x = y;
}
void foo() {
cout << x << endl;
}
~test() {
}
};
int main() {
test a(100);
test b = 10;
a.foo();
b.foo();
return 0;
}
I expect the compiler not to accept the second line in the main function (test b = 10;) while it accepts. Indeed, it casts the integer (10) to an object of type test constructed as test(10). This is of course because test has a constructor of type test(constint).
However, logically this should not happen. The object of type "test" can be a much more complicated object than a simple integer and casting the integer in this way is meaningless.
I was wondering why this happens and more importantly how one can prevent the compiler from this stupid automatic casting?
class test {
private:
int x;
public:
test(constint y) {
cout << "y = " << y << endl;
x = y;
}
test & operator=(const test & rhs)
{
cout << "Assignment" << endl;
x = rhs.x;
return *this;
}
void foo() {
cout << x << endl;
}
~test() {
}
};
You'll notice the assignment operator is never called. When you declare an object and assign it in the same expression, it doesn't first construct the default object and then assign, it constructs using the right hand side as the parameter for the constructor.
Change test b = 10
to
1 2
test b;
b = 10;
And you'll get an error that you don't have a default constructor. Fix that, and THEN you will see the problem you think you are seeing now - "10" will be used to automatically construct a test object when the compiler tries to call "test & operator=(const test & rhs)". It's not exactly 'casting' to an object of type test, but similar. As abramus pointed out, specifying your constructor as being explicit will prevent this behavior.