cin、cout 与 scanf、printf 的效率比较

来源:互联网 发布:医脉通官 软件 编辑:程序博客网 时间:2024/04/29 22:16

转自:http://blog.csdn.net/zq_onlytime/article/details/44900081

很早就知道,c的scanf(printf)比c++的快。刷题时尤其明显,在这上面超时是常有的事儿。

但,这是别人告诉我的,c快。

为什么快?

从网上借鉴一个例子做个简单测试:

1.cpp //向一个文件里输入1000000个随机数

#include<iostream>#include<fstream>#include<cstdlib>using namespace std;const int num=1000000;int main(){    ofstream file("data");    for(int i=0;i<num;i++)    {            file<<rand()<<' ';            if((i+1)%20==0)            file<<endl;    }    return 0;}

2.cpp //用cin读取这1000000个随机数

#include<iostream>#include<ctime>#include<cstdio>#include<windows.h>using namespace std;const int num=1000000;int main(){    freopen("data","r",stdin);    int i,n,start,end;    start=clock();    for(i=0;i<num-2;i++)    cin>>n;    end=clock();    cout<<double(end-start)/CLOCKS_PER_SEC<<endl;    Sleep(5000);    system("pause");    return 0;}

结果: 耗时 5.281秒

3.cpp //用scanf读取这1000000个数

#include<ctime>#include<cstdio>#include<stdlib.h>#include<windows.h>#include<iostream>using namespace std;const int num=1000000;int main(){    freopen("data","r",stdin);    int i,n,start,end;    start=clock();    for(i=0;i<num;i++)    scanf("%d",&n);    end=clock();    //cout<<double(end-start)/CLOCKS_PER_SEC<<endl;    printf("%f\n",double(end-start)/CLOCKS_PER_SEC);    system("pause");    Sleep(5000);    return 0;}                     

结果: 耗时 0.437秒

结论:scanf真的比cin快。竟快10倍。
运行环境,xp,DEV-C++。

比较合理的解释:默认情况,cin与stdin总是保持同步的,也就是说这两种方法可以混用,而不必担心文件指针混乱,同时cout和stdout也一样,两者混用不会输 出顺序错乱。正因为这个兼容性的特性,导致cin有许多额外的开销,如何禁用这个特性呢?只需一个语句 std::iOS::sync_with_stdio(false);,这样就可以取消cin于stdin的同步了,此时的cin就与scanf差不多 了。

另一种解释: cout在输出时总是要先将输出的存入缓存区。而printf直接调用系统进行IO,它是非缓存的。所以cout比printf慢。(这种解释,我没有验证)


补充1:

[待验证]
在g++中,cout通常比printf的性能高。

影响cout的性能通常有两个因素,一是某些实现例如VS用printf实现cout,当然printf比cout快;二是iostream默认情况下是与stdio关联在一起的,就是cout在运行时,会刷新stdio,这个操作会拖慢cout的性能。但g++的cout并不是用printf实现的,即使不去掉与stdio的关联,cout已经比printf要快,在我的三星7寸笔记本中,通常要快三分一左右,如果通过std::ios_base::sync_with_stdio( false )去掉与stdio的关联,甚至比printf快几乎十倍。

补充2:

流输入输出的有点:
1.流输入输出对于基本类型来说使用很方便,不用手写格式控制字符串。
2.对于标准库的一些class来说,显然重载操作符也比自己写格式控制字符串要方便很多。
3.对于复杂的格式可以进行自定义操作符。
4.可读性更好(这个很多人有不同意见,见仁见智了)。

其实原理上来说:流操作的效率比printf/scanf函数族更高,因为是在编译期确定操作数类型和调用的输出函数,不用在运行期解析格式控制字符串带来额外开销。不过标准流对象cin/cout为了普适性,继承体系很复杂,所以在对象的构造等方面会影响效率,因此总体效率比较低。如果根据特定的场景进行优化,效率可以更高一点。

0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 华为手机进水了显示耳机模式怎么办 苹果6s突然变成耳机模式怎么办 华为手机出现耳机标志没声音怎么办 苹果手机微信变成耳机模式怎么办 5s不能用4g网络怎么办 华为麦芒四手机系统乱了好卡怎么办 信翼路由器登录密码忘了怎么办 苹果手机电信4g信号变3g怎么办 苹果7手机4g变3g怎么办 朵唯v3逆客手机不支持计步怎么办 移动卡升级4g后网络不好怎么办 电信办宽带送的手机卡不用了怎么办 移动华为悦盒遥控器丢了怎么办 移动签了两年套餐不想用了怎么办 华为手机隐私空间密码忘记了怎么办 华为的隐私空间密码忘记了怎么办 格力新机没密码开不了怎么办 百度下载谷歌浏览器网页错误怎么办 华为手机进水开不了机怎么办开 华为7x金属外壳掉漆了怎么办 华为麦芒6连接蓝牙音响卡顿怎么办 华为芒麦6恢复出厂设置怎么办 华为麦芒4下拉通知栏没反应怎么办 怎么看华为麦芒6信号差怎么办 华为手机锁屏密码忘了怎么办 苹果手机进水后手机卡无服务怎么办 摩拜单车绑定的手机号注销了怎么办 摩拜单车注册的手机号注销了怎么办 摩拜单车注册手机号换了怎么办 被手机店骗话费送合约机怎么办 机蜜租赁的手机丢了怎么办 合约机返话费手机掉了怎么办 手机摔坏了开不了机怎么办 华为魅特10屏幕锁住了怎么办 电信送的路由器只有一个端口怎么办 苹果手机5c屏幕死机了怎么办 日版苹果手机显示无服务怎么办 iphone有锁4g变3g怎么办 耳机胶套脱落掉入耳朵怎么办 苹果笔记本电用完了开机了怎么办 华为荣耀5x锁屏密码忘了怎么办