在这些c ++示例中:
1. int operator+ ( Jazz &lhs,Jazz &rhs );
2. Jazz & Jazz operator= (const Jazz &);
3. Jazz & operator+ ( const Jazz & )
我理解c ++中运算符重载的基本概念。 我不知道的是:
在第二个例子中,我们是否需要在重载 operator = 之前声明和定义复制构造函数?
如何区分成员和非成员运算符重载?
第一个例子是非成员,但它可以访问类实例,并使用它们吗?
第三个例子也是非成员,但它是Jazz类型的?
请有人解释一下。谢谢。
答案 0 :(得分:2)
示例一必须是非成员运营商。因为operator+
如果是非成员,则有一个或两个参数,但如果是成员则为零或一个。它没有Jazz
的特殊访问权限,它与此方面的任何其他功能相同。如果您想要对Jazz
赋予特殊权限,您可以将其声明为friend
(再次与其他任何功能一样)。
示例2必须是成员,这只是C ++的规则,operator=
必须是成员函数。您也不必声明复制构造函数。只是这是非常常见的,如果你需要一个复制构造函数,你还需要一个赋值运算符,反之亦然。
示例三可以是成员或非成员(参见答案1)。如果它是一个成员,它将定义一个二元运算符(即用于a + b
之类的用途),但如果它是非成员,则它将定义一元运算符(即用于+a
之类的用法)。无论哪种方式,我都不认为这是'爵士'的类型。它可能是Jazz类的成员,但它不一定是,它可能完全是一个不同类的成员。
答案 1 :(得分:0)
如何区分成员和非成员运算符重载?
成员和非成员运算符重载之间的一个区别是,对于声明/定义为成员函数的重载,参数数量减少一个。对于一元运算符,您没有参数,对于二元运算符,您有一个。
有些重载无法在类范围之外声明/定义,operator =()就是其中之一。
此外,成员函数的作用域不同,如果没有声明类型的实例,则无法调用它,除非它是静态的。一些运算符,如operator =(),它们必须是成员函数,但不允许它们是静态的。
第一个例子是非成员,但它可以访问类实例,并使用它们吗?
operator +()是一个带有两个参数的二元运算符,表示一个自由函数。
如果类型定义了允许operator +()在两个实例上工作的公共接口。或者,如果操作符被声明为友元函数,则授予该类型的私有和受保护成员的函数访问权。
在上面的例子中,返回类型非常“有趣”,因为两个Jazz实例的总和显然应该是一个int。你可能想问这个问题。
第三个例子也是非成员,但它是Jazz类型的?
此运算符通常称为复制赋值运算符,如上所述,必须是某种类型T的非静态成员函数。
标准没有强制要求返回类型,它可能只是 void ,但是通常会向受理人返回非const引用,即正在分配的类型T的实例到。
T& T::operator(const T& rhs)
返回引用的一个原因是,然后可以链接分配:
T t;
T t2;
T t3;
t = t2 = t3; // assignment chaining
另一个原因是,在某些情况下,标准库期望operator =()返回对用户定义类型的受让人的引用。
对于C和C ++中相当完整的运算符列表,您可以参考this。