我正在编写一个将文件读入内存的C库。它会跳过文件的前54个字节(标题),然后将余数作为数据读取。我使用fseek来确定文件的长度,然后使用fread读取文件。

循环运行一次然后结束,因为达到了EOF(没有错误)。最后,bytesRead = 10624,ftell(stream)= 28726,缓冲区包含28726个值。我希望fread读取30,000字节,当达到EOF时文件位置为30054。

C不是我的母语所以我怀疑我在某处犯了一个愚蠢的初学者错误。

代码如下:

const size_t headerLen = 54;

FILE * stream;
errno_t ferrno = fopen_s( &stream, filename.c_str(), "r" );
if(ferrno!=0) {
  return -1;
}

fseek( stream, 0L, SEEK_END );
size_t bytesTotal = (size_t)(ftell( stream )) - headerLen; //number of data bytes to read
size_t bytesRead = 0;
BYTE* localBuffer = new BYTE[bytesTotal];
fseek(stream,headerLen,SEEK_SET);
while(!feof(stream) && !ferror(stream)) {
    size_t result = fread(localBuffer+bytesRead,sizeof(BYTE),bytesTotal-bytesRead,stream);
    bytesRead+=result;
}

根据您使用的参考,很明显添加“b”。模式标志是答案。寻求骷髅徽章的提名。 : - )

此参考在第二段中讨论它,第二句(虽然不在他们的表中)。

MSDN 不讨论二进制文件标志直到页面中间。

OpenGroup 提到了“b”的存在。标签,但声明它“应该没有效果”。

有帮助吗?

解决方案

也许这是一个二元模式问题。尝试使用" r + b" 作为模式打开文件。

编辑:正如评论" rb" 中所述,可能更符合原始意图,因为" r + b" 将打开它进行读/写," rb" 是只读的。

其他提示

另外值得注意的是,将binmode.obj简单地包含在你的链接命令中将为你打开所有文件。

基于之前答案的解决方案:

    size_t bytesRead = 0;
    BYTE* localBuffer = new BYTE[bytesTotal];
    fseek(stream,headerLen,SEEK_SET);
        while(!feof(stream) && !ferror(stream)) {
        size_t result = fread(localBuffer+bytesRead,sizeof(BYTE),bytesTotal-
        bytesRead,stream);
    bytesRead+=result;
}
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top