我还在C++的基础学习过程中,在操作符重载部分,我无法理解iostream重载操作符的函数调用步骤。
我的困惑来自以下事实:当“重载 iostreeam 函数是通过友元命令在我的类定义之外定义的”时,下面的 C++ 代码可以区分基本类型数据 iostream 调用和类 iostream 调用。请看下面的示例。
#ifndef PHONENUMBER_H
#define PHONENUMBER_H
#include <iostream>
#include <string>
class PhoneNumber
{
friend std::ostream &operator<<( std::ostream &, const PhoneNumber & )
friend std::istream &operator>>( std::istream &, PhoneNumber & )
private:
std::string areaCode;
std::string exchange;
std::string line;
};
#endif
现在是重载函数定义。
#include <iomanip>
#include "PhoneNumber.h"
using namespace std;
ostream &operator<<( ostrea &output, const PhoneNumber &number )
{
output << "(" number.areaCode << ")" << number.exchange << "-" << number.line;
return output;
}
istream &operator>>( istream &input, PhoneNumber &number )
{
input.ignore();
input >> setw( 3 ) >> number.areaCode;
input.ignore( 2 );
input >> setw( 3 ) >> number.exchange;
input.ignore();
input >> setw( 4 ) >> number.line;
return input;
}
现在是主要功能。
#include <iostream>
#include "PhoneNumber.h"
using namespace std;
int main()
{
PhoneNumber phone;
cout << "Enter phone number in the form (123) 456-7890" << endl;
cin >> phone;
cout << "The phone number entered was: ";
cout << phone << endl;
}
据我了解,通常函数调用(甚至运算符重载函数)必须遵循声明格式。因此,要调用重载 <<(或 >>)运算符函数,用户必须编写如下行:'ostream a;'接着是 'cin >> ( a, phone );'。同样在上面的示例中,它看起来像“cin >> phone;”这一行会被注意到并直接指向 friend 功能。按照我的理解,运算符(operator)调用“cin >> phone”将首先查看 PhoneNumber.h 声明。但是,运算符声明不在 PhoneNumber.h 中。它只是作为 friend 被“提及”。 (我对'friend'命令的理解是该类将简单地授予非成员函数(或类)访问其私有(private)数据或成员函数的权限。)因此,调用应该混淆编译器调用显式运算符函数以上代码,或 iostream 中的隐式运算符函数。
我想我的问题是: 1. 运算符“<<”和“>>”调用的格式与它们的声明方式有何不同? 2. .h 文件中未“声明”的运算符(operator)调用如何识别? C++ 如何知道跳过 .h 并直接跳转到用户定义的运算符函数?
最佳答案
您的问题中有一些明显的误解,但其余的我无法真正解析。希望以下内容足以解决您的疑问。
这个:
cin >> x;
是这个的语法糖(更像是你想象中的函数调用语法):
cin.operator>>(x);
或者有时(在这种情况下)这样:
operator>>(cin, x);
你不能随意为其中任何一个发明额外的参数!
关于C++ 类 iostream 重载,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29314516/