Car*_*rum 14
在标准C中,fseek/ ftelldance几乎是城里唯一的游戏.你做的其他任何事情至少在某种程度上取决于你的程序运行的特定环境.不幸的是,舞蹈也有你所链接的文章中描述的问题.
我猜你总是可以读出文件中的所有内容,直到EOF并保持跟踪 - fread()例如.
该文章声称fseek(stream, 0, SEEK_END)是一种不定义的行为,引用了一个不合时宜的脚注.
脚注出现在处理面向广播的流的文本中,这些流是对它们执行的第一个操作的流是对宽字符的操作.
这种未定义的行为源于两个段落的组合.首先§7.19.2/ 5说:
- 二进制宽向导流具有归因于文本和二进制流的文件定位限制.
文本流(第7.19.9.2/4节)对文件定位的限制是:
对于文本流,要么
offset是零,要么offset是早先成功调用ftell与同一文件关联的流上的函数返回的值,并且whence应该是SEEK_SET.
这使得面向广泛的流的fseek(stream, 0, SEEK_END)未定义行为.对于面向字节的流,没有像§7.19.2/ 5这样的规则.
此外,当标准说:
二进制流不需要有意义地支持值为的
fseek调用.whenceSEEK_END
这并不意味着它的未定义行为.但是如果流支持它,那没关系.
显然这是允许二进制文件具有粗粒度粒度,即大小是多个磁盘扇区而不是多个字节,因此允许未指定数量的零神奇地出现在二进制文件的末尾.SEEK_END在这种情况下无法得到有意义的支持.其他示例包括管道或无限文件/dev/zero.但是,C标准无法区分这些情况,因此如果您想考虑这一点,就会遇到与系统相关的调用.