面试题答案
一键面试常见限制
- 只能重载为非成员函数:因为 << 和 >> 运算符的左侧操作数通常是流对象(如
std::cout
或std::cin
),而流对象属于标准库,不能在标准库类上直接添加成员函数。如果重载为成员函数,语法就会变成streamObject.operator<<(data)
,这不符合习惯的流操作语法streamObject << data
。 - 不能改变运算符的优先级和结合性:C++ 规定了运算符的优先级和结合性,重载运算符时不能改变这些特性。例如,
<<
运算符本身的优先级和结合性是从左到右,重载后依然如此。 - 参数个数限制:对于二元运算符(如 << 和 >>),重载函数必须有两个参数,第一个参数通常是流对象的引用,第二个参数是要输出或输入的数据类型。不能随意改变参数个数以适配特定需求。
针对“只能重载为非成员函数”限制的解决方案
可以通过友元函数来解决这个问题。友元函数虽然不是类的成员函数,但它可以访问类的私有和保护成员。以下是一个简单示例:
#include <iostream>
class MyClass {
private:
int value;
public:
MyClass(int v) : value(v) {}
// 声明 << 运算符重载为友元函数
friend std::ostream& operator<<(std::ostream& os, const MyClass& obj);
};
// 定义 << 运算符重载
std::ostream& operator<<(std::ostream& os, const MyClass& obj) {
os << "MyClass value: " << obj.value;
return os;
}
int main() {
MyClass obj(42);
std::cout << obj << std::endl;
return 0;
}
在上述代码中,operator<<
被声明为 MyClass
的友元函数,这样它就能访问 MyClass
的私有成员 value
,同时满足了流运算符重载为非成员函数的要求。