| 网站首页 | 业界新闻 | 小组 | 威客 | 人才 | 下载频道 | 博客 | 代码贴 | 在线编程 | 编程论坛
欢迎加入我们,一同切磋技术
用户名:   
 
密 码:  
共有 6307 人关注过本帖, 1 人收藏
标题:关于c++中istream和ostream和问题
只看楼主 加入收藏
海盗许毅
Rank: 2
等 级:论坛游民
帖 子:12
专家分:15
注 册:2012-4-30
结帖率:100%
收藏(1)
已结贴  问题点数:20 回复次数:5 
关于c++中istream和ostream和问题
        最近在学c++,遇到一个问题,cin和cout分别是istream和ostream的对象,那是不是我也可以用这两个类定义两个对象来替代cin,cout呐?
         还有就是cin的内部是如何实现的?是不是这样的:istream& oprertator<<(int ){   }?
我知道它是重载了好的数据类型的,但是{ }里面是如何实现的?请高手赐教,谢谢了。




[ 本帖最后由 海盗许毅 于 2012-5-5 18:16 编辑 ]
搜索更多相关主题的帖子: 如何 
2012-05-05 18:07
pangding
Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19
来 自:北京
等 级:贵宾
威 望:94
帖 子:6784
专家分:16751
注 册:2008-12-20
收藏
得分:19 
对实现感兴趣很好。初学者一般开始时都会对 io 比较感兴趣,但事实上,这可能也是标准库里最复杂的一部分。

一般意义上讲,你很难自己写一段代码来代替 cin 或者 cout。因为 io 的很多过程都要和操作系统交互,而 C++ 这门语言又是跨平台跨系统的,所以编译器底层也要在很多不同的系统上实现,才能最终保证跨平台的实现。

你也许会用其它流操作来读取或写入磁盘文件,拿这个举例可能更好理解。而且本质上读取和写入磁盘文件与读取和写入标准IO也没什么分别。
当你打开一个文件后,库函数会为你构造一个流对象关联到你指定的磁盘文件,这个对象的一个很重要的私有成员是一块缓冲区。你所有的插入(或读取)命令都是针对缓冲区进行的,而不是直接操作磁盘文件。当缓冲区写满(或读空)或者你要求强制刷新(或同步)的时候,库函数才会调用系统函数,真正读写磁盘文件。事实上,你完全可以自己调用系统函数,而不使用标准库的那套东西。但这一般会更加麻烦:要么你就得自己管理缓冲区,这会增加实现的难度(而且除了极少数的情况,一般来说效率也不如库函数高)。或者完全放弃缓冲技术,但这样效率更加低下,一般会比使用库函数慢数百到数千倍(除了缓冲这个技术本身能提高IO效率以外,系统函数的调用速度本来就比库函数要慢,因为它还需要诸如核查调用进程的权限等等其它额外的操作)。
标准输入输出是在 main 函数开始执行之前就初始化完毕的,它的缓冲区也在那个时候就准备好了。当然你可以自己建个流关联到那个缓冲区上,但这似乎跟你说的自己定义两个对象来代替 cin 和 cout 也相去甚远。对于很多库函数来说,从标准IO上读写文件和一般文件IO没什么区别。有的时候只有操作系统关心那个所谓的文件究竟是磁盘文件还是特殊设备。

至于你问的 << 是怎么实现的。
简单来说,如果要插入的对象是 char 或者 char* 之类的,那么就会直接插入到那个缓冲区里。这时外像对齐方式呀,输出宽度之类的选项会影响插入的行为。
如果是 int, float 之类的东西,那会先把它们格式化成字符串。这时设置的基底呀,精度之类的选项会影响到参数的格式化。格式成字符串之后,会按照字符串的插法再往缓冲区里写。
当然在这些过程中,库函数还会监测流的状态。比如流的状态是否正常,是否可以写入。还会监视缓冲区是不是写满了。另外格式化和插入的过程中都有可能会出现错误,那么库函数还会在设置好相应的错误状态后,把接到的异常 rethrow。
收到的鲜花
  • 海盗许毅2012-05-06 13:02 送鲜花  3朵   附言:我很赞同
2012-05-06 10:19
海盗许毅
Rank: 2
等 级:论坛游民
帖 子:12
专家分:15
注 册:2012-4-30
收藏
得分:0 
回复 2楼 pangding
虽然我只能理解版主说的部分内容,但是还是非常感谢版主的热心帮助。这说明我对这方面的理解还不到位,我会不停努力的。以后还请版主多多赐教。
2012-05-06 13:06
cosdos
Rank: 9Rank: 9Rank: 9
来 自:ShangHai
等 级:蜘蛛侠
威 望:6
帖 子:2109
专家分:1385
注 册:2007-6-19
收藏
得分:1 
io 一直与平台密切相关。

—>〉Sun〈<—
2012-05-06 16:49
BianChengNan
Rank: 8Rank: 8
等 级:贵宾
威 望:13
帖 子:302
专家分:972
注 册:2011-11-30
收藏
得分:0 
以下是引用pangding在2012-5-6 10:19:00的发言:

对实现感兴趣很好。初学者一般开始时都会对 io 比较感兴趣,但事实上,这可能也是标准库里最复杂的一部分。

一般意义上讲,你很难自己写一段代码来代替 cin 或者 cout。因为 io 的很多过程都要和操作系统交互,而 C++ 这门语言又是跨平台跨系统的,所以编译器底层也要在很多不同的系统上实现,才能最终保证跨平台的实现。

你也许会用其它流操作来读取或写入磁盘文件,拿这个举例可能更好理解。而且本质上读取和写入磁盘文件与读取和写入标准IO也没什么分别。
当你打开一个文件后,库函数会为你构造一个流对象关联到你指定的磁盘文件,这个对象的一个很重要的私有成员是一块缓冲区。你所有的插入(或读取)命令都是针对缓冲区进行的,而不是直接操作磁盘文件。当缓冲区写满(或读空)或者你要求强制刷新(或同步)的时候,库函数才会调用系统函数,真正读写磁盘文件。事实上,你完全可以自己调用系统函数,而不使用标准库的那套东西。但这一般会更加麻烦:要么你就得自己管理缓冲区,这会增加实现的难度(而且除了极少数的情况,一般来说效率也不如库函数高)。或者完全放弃缓冲技术,但这样效率更加低下,一般会比使用库函数慢数百到数千倍(除了缓冲这个技术本身能提高IO效率以外,系统函数的调用速度本来就比库函数要慢,因为它还需要诸如核查调用进程的权限等等其它额外的操作)。
标准输入输出是在 main 函数开始执行之前就初始化完毕的,它的缓冲区也在那个时候就准备好了。当然你可以自己建个流关联到那个缓冲区上,但这似乎跟你说的自己定义两个对象来代替 cin 和 cout 也相去甚远。对于很多库函数来说,从标准IO上读写文件和一般文件IO没什么区别。有的时候只有操作系统关心那个所谓的文件究竟是磁盘文件还是特殊设备。

至于你问的 << 是怎么实现的。
简单来说,如果要插入的对象是 char 或者 char* 之类的,那么就会直接插入到那个缓冲区里。这时外像对齐方式呀,输出宽度之类的选项会影响插入的行为。
如果是 int, float 之类的东西,那会先把它们格式化成字符串。这时设置的基底呀,精度之类的选项会影响到参数的格式化。格式成字符串之后,会按照字符串的插法再往缓冲区里写。
当然在这些过程中,库函数还会监测流的状态。比如流的状态是否正常,是否可以写入。还会监视缓冲区是不是写满了。另外格式化和插入的过程中都有可能会出现错误,那么库函数还会在设置好相应的错误状态后,把接到的异常 rethrow。

学习了,版主

我的群:149544757 C/C++/Assembly 喜欢交流的朋友进,进群请写消息
2012-05-09 09:33
celavi
Rank: 1
等 级:新手上路
帖 子:1
专家分:0
注 册:2012-10-16
收藏
得分:0 
以下是引用pangding在2012-5-6 10:19:00的发言:

对实现感兴趣很好。初学者一般开始时都会对 io 比较感兴趣,但事实上,这可能也是标准库里最复杂的一部分。

……

写的很好,谢谢!
2012-10-16 17:43
快速回复:关于c++中istream和ostream和问题
数据加载中...
 
   



关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.025124 second(s), 8 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved