关于最不起眼的输入以及宽字符

本文探讨了在C语言编程中getchar()和printf()函数在缓冲区处理上的问题,并提供了实验观察结果,同时给出了针对这些问题的解决方案建议。
我的旧闻,原来发布在Spaces.live.com

来是在写一个水准测量的校验程序的,结果在处理用户界面时,我遇到相当不爽的问题——getchar()和printf()似乎在buf的问题上不能按照最好的思路协调。结果我的程序就在神经错乱中献出了最宝贵的生命。
 
一个向来都不在考虑之中的输入输出部分开始让我郁闷,疯狂和吃东西。奋战的两点的东西,结果让我第二天一整天的测量都是累得半死,而且要算大量的数据——这个一度让我差点要重测两天的路程。
 
根据K&R的解释,stdin和stdout是extern FILE _iob[OPEN_MAX]的0和1入口,这个_iob[]由系统实现。同时stdin和stdout都是缓冲了的,buf的大小大概为1024(老 unix)或者4096(BSD)。由此我们可以得知,c = getchar()的写法,c并非立刻得到值,而是当'/n'进入后或者buf满了后,缓冲区清空后得到的。我写了一个小程序:
int c, x;
sprintf(stderr, "%d", clock());
c = getchar();
x = c;
while(EOF != (c = getchar)) {
sprintf(stderr, "Sec %d", clock());
if ( c != x) {
sprintf(stderr, "sec %d", clock());
fflush(NULL);
putchar(c);
fflush(NULL);
sprintf(stderr, "sec %d", clock());
}
x = c;
sprintf(stderr, "sec %d", clock());
}
然后你就可以大量的输入了,然后观察值得变化。很明显的,第一个输出值比第二个要早大概4的速度(我猜是ms),后面的值是很连续的,可见,又一个缓冲过程。但是大概每两个输出(或者4个)就会又一个时间的变化,我猜测是乱序执行或者是合并指令之类优化的杰作。
 
在comp.lang.c的历史文献里,有人指出printf()和getchar()在连用时,当顺序不同时,往往有不 同结果,或者程序对user的动作期待是不同的(比较了Linux和SGI后),并且建议在interactive类型的程序中使用strtod()之类 的函数从手工buf中读数("scanf/getchar sequence problem", Eric Sosman, Apri. 7th, 2005, 11:20 p.m.)。
 
另外,当scanf(...)后,用getchar(),结果会成为'/n',即无论是scanf()还是getchar()都需要的LR(ascii 0xA)还是会压入buf队列的。
 
宽字符部分:wchar_t c;然后再直接scanf("%c", &c);结果C会完整得存储GBK编码(也可能是Unicode 16)。
 
P.S. 我的malloc()莫名其妙的return NULL,而且是在一个极小的程序中,内存充足时发生的。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值