我知道这是非常基本的,但我有点猜测到这一点。
Foo只是一个具有来自字符串类的私有继承的对象,这就是我投射它的原因。使用Primer C ++(Prata's)中的示例
所以,如果我有这样的功能:
istream & operator>>(istream & is, Foo & f)
{
is >> (string &)f;
return is;
}
int main()
{
Foo f;
cin >> f;
}
所以,一旦cin>> f被命中,函数被调用,而now字符串存储在istream引用中。 istream对象现在返回,现在......?返回的istream对象的内容(字符串)现在是否自动放在f中?或者我是否错过了解cin如何工作的一步?
另外,如果我这样做:
int x;
cin >> f >> x;
它会如何隐含的样子?喜欢(cin)>> X?
最后,还有一件简单的事情。如果在一个函数(包含一个ostream引用)中,我在循环遍历每个数组项并执行此操作:
for(int i=0;i < 5;i++)
{
os << array[i] << "\n";
}
ostream对象是否只是复合了每个数组项?
答案 0 :(得分:3)
如果使用普通函数调用替换重载运算符,则变得非常容易。 cin >> f
只是转换为:
operator >>(cin, f);
现在将cin >> f >> x
视为(cin >> f) >> x
。这转化为:
operator >>(operator >>(cin, f), x);
由于第一个运算符返回cin
,因此在执行期间,它实际上变为:
operator >>(cin, x);
原始数据类型(如int
)通常在流类本身内重载,因此它实际上如下所示:
cin.operator >>(x);
您可以自行解决此问题,以回答有关ostream
的问题 - 它的工作原理完全相同。
答案 1 :(得分:1)
执行cin >> f
时,重载决策会选择重载的istream >>
重载并调用它。然后,在您的重载中,您从流中提取string
,该流调用带有istream和>>
的{{1}}重载。
请注意,从string
派生出来是非常不寻常的,甚至是私下的。相反,您应该使用组合:拥有类型为std::string
的成员变量。
你的演员阵容很混乱;如果你有一个std::string
类型的成员变量,那么你可以使用更自然的语法来提取它:
std::string
is >> f.stringmembervariable;
首先从cin >> f >> x
中提取Foo
并将其存储在cin
中,然后从f
中提取int
并将其存储在cin
中x
。假设所有>>
重载遵循返回它们被传递的istream的约定,它实际上就像你说的那样:
cin >> f;
cin >> x;
这就是你应该从>>
重载返回istream的原因,这样就可以像这样链接提取。
至于你的上一个问题,在循环内部,无论<<
的类型是什么,都会调用重载的ostream array[i]
运算符。
答案 2 :(得分:1)
istream & operator>>(istream & is, Foo & f)
{
is >> (string &)f;
return is;
}
istream& operator>>(istream& is, string& f)
(好吧,basic_istream<T>&, basic_sttring<T>&
)已经存在。所以,虽然你可以这样做,但为什么呢?
所以,一旦cin&gt;&gt; f被命中,函数被调用,而now字符串存储在istream引用
中
不,流被istream& operator>>(istream& is, string& f)
消耗,它将字符串(的存储空间)设置为包含消耗字节的表示。
然后返回对istream的引用。
int x;
cin >> f >> x;
相当于:
int x;
(cin >> f) >> x;
因为操作员关联规则,并且“真的”:
int x;
std::operator>>( ::operator>>(cin, f), x ) ;
其中两个operator>>
是op>>
的两个不同的重载版本,也就是说,你的版本(在全局命名空间中)采用了一个istream和一个Foo是内部的一个,返回对istream的引用,在转向中是外部的第一个参数,std命名空间中的一个带有istream和int。
ostream对象是否只是复合了每个数组项?
每个对象,无论array [n]是什么类型,都会被添加到ostream, in sequence ,添加到流中,后跟换行符。所以“compunded”是表达它的坏方法,但是是的。当然,需要存在op<<( ostream&, const X&)
,其中“X”是数组[n]的任何类型(或者可以隐式转换为)。
答案 3 :(得分:0)
当你这样做时:
cin >> f;
你是正确的,你的操作员函数将被调用,而cin上的任何字符串现在都将存储在f中。
当你这样做时:
cin >> f >> x;
真正发生的是你的函数被调用与之前相同,但它返回cin。由于没有重载&gt;&gt;为istream和int定义,cin将被正常处理。
首先,计算机会计算:
cin >> f;
你的功能超载了。然后计算机计算:
cin >> x;
这是cin和整数的正常操作。
您的行也会发生同样的事情:
os << array[i] << "\n";
在那:
os << array[i];
首先处理,然后:
os << "\n";
得到处理。
从技术上讲,在这两种情况下,您的流对象都会被返回,但是没有使用返回的值,所以它只是被丢弃了。这就像一条线说的那样:
sqrt(81);
由于没有用于存储返回值的变量,计算机将计算该值,然后将其丢弃(或者如果编译器是智能的,则完全跳过它)。