result = oneHalf * 2; // error! (with explicit ctor);
// can’t convert 2 to Rational
result = 2 * oneHalf; // same error, same problem
支持混合模式操作失败了,但是至少两个语句的行为将步调一致。
然而,你的目标是既保持一致性又要支持混合运算,也就是说,一个能使上面两个语句都可以编译的设计。让我们返回这两个语句看一看,为什么即使 Rational 的构造函数不是显式的,也是一个可以编译而另一个不行:
result = oneHalf * 2; // fine (with non-explicit ctor)
result = 2 * oneHalf; // error! (even with non-explicit ctor)
其原因在于仅仅当参数列在参数列表中的时候,它们才有资格进行隐式类型转换。而对应于成员函数被调用的那个对象的隐含参数—— this 指针指向的那个——根本没有资格进行隐式转换。这就是为什么第一个调用能编译而第二个不能。第一种情况包括一个参数被列在参数列表中,而第二种情况没有。
你还是希望支持混合运算,然而,现在做到这一点的方法或许很清楚了:让 operator* 作为非成员函数,因此就允许便一起将隐式类型转换应用于所有参数:
class Rational {
... // contains no operator*
};
const Rational operator*(const Rational& lhs, // now a non-member
const Rational& rhs) // function
{
return Rational(lhs.numerator() * rhs.numerator(),
lhs.denominator() * rhs.denominator());
}
Rational oneFourth(1, 4);
Rational result;
result = oneFourth * 2; // fine
result = 2 * oneFourth; // hooray, it works!
这样的确使故事有了一个圆满的结局,但是有一个吹毛求疵的毛病。operator* 应该不应该作为 Rational 类的友元呢?
Things to Remember
·如果你需要在一个函数的所有参数(包括被 this 指针所指向的那个)上使用类型转换,这个函数必须是一个非成员。
|
您将承担一切因您的行为、言论而直接或间接导致的民事或刑事法律责任
留言板管理人员有权保留或删除其管辖留言中的任意内容 本站提醒:不要进行人身攻击。谢谢配合。 |