fread/fwrite size and count

5

我对于fread/fwrite中参数size和count的顺序存在疑惑。如果我想从文件fp中读取8kb的数据,以下哪种方式更高效?

fread(data,1,8192,fp)
fread(data,8192,1,fp)

同时,我需要担心字节序问题吗?

2个回答

11

它们完全等同。至于字节序,这取决于你正在读取什么。通常,它将是一组字节的缓冲区,然后你将根据编写时使用的格式“取消格式化”它们。而且由于是字节,字节序不起作用。

编辑:

正如simonc指出的那样(然后删除了,因为他没有100%正确——但他的观点是正确的):关于返回值有一个差别(您需要使用它来知道函数是否运行成功)。fread( buffer, 8192, 1, fp )将返回0或1,只有在读取了全部8192个字节时才会返回1。此外,Posix表示,对于部分读取的对象,缓冲区的内容未指定。实际上,缓冲区将填充尽可能多的字节,但由于您不知道那是多少,所以这并没有太大帮助。总之,您应始终使用fread( buffer, 1, 8192, fp );(因为除了一组字节的缓冲区外,使用此函数没有意义)。


4
他正在读取字节。字节没有字节序的概念。一旦他读取了这些字节,他必须按照文件格式的规格来解释它们。通常应该在不考虑字节序的情况下完成这项工作。 - James Kanze
@fvdalcin 而且,这些函数唯一合理的用途是 unsigned char buffer[8192]; fread( buffer, 8192, 1, fp );。之后,您必须根据指定的文件格式解释缓冲区。 - James Kanze
谢谢。它们的效率是否相同? - danny
@danny 两者都会受到磁盘访问速度和从操作系统传输数据到进程中的限制。我不会担心这里的效率差异;与其他一切相比,任何差异都将是微不足道的。 - James Kanze
1
@James Kanze 注意:fread() 可以用于除磁盘和 stdin 之外的其他 I/O,例如从串行 I/O 中读取部分 8192 块。 - chux - Reinstate Monica
显示剩余3条评论

3

它们并不完全等同。

fread() 的设计存在问题。它的设计忽略了文件末尾可能出现部分读取的情况,这种情况无法通过其返回值来表示,而其返回值是以您指定的大小单位计算的。

您应该仅在大小为1且长度为您期望的字节数时使用fread()。这是您能够正确处理此类情况的唯一方式。对于char以外的类型,这意味着提供sizeof char作为大小和n*sizeof T作为长度,其中n是您期望的T的数量。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接