基于filesize分配内存的数量是否正确?

问题描述 投票:-2回答:1

我想将我的文件的内容存储在动态字符串指针值中。这是我的代码:

    char *strPtr = NULL;
    char tmpChar = "";
    inputFile = fopen(input_file, "r");

    fseek(inputFile, 0, SEEK_END);   // seek to end of file
    fileSize = ftell(inputFile);    // get current file pointer
    rewind(inputFile);
    strPtr = (char*) realloc(strPtr, fileSize * sizeof(char));
    int counter = 0;

    while ((tmpChar = fgetc(inputFile)) != EOF)
    {
        strPtr[counter] = tmpChar;
        counter++;
        if (counter == fileSize)
            printf("OK!");
    }
    printf("Filesize: %d, Counter: %d", fileSize,counter);

现在我的问题...对于最后一个printf,我得到2个不同的值,例如:Filesize 127&Counter 118.在我的strPtr-Variable的END处添加了一个错误的输入,如“ÍÍÍÍÍÍÍÍÍýýýýüe”。

Notepad ++还在文件的末尾说我在127位,那么关于118的问题是什么?

c file pointers counter filesize
1个回答
2
投票

如果在Windows上以文本模式(默认)打开文件,则CRT文件函数会将任何\r\n转换为\n。这样做的效果是您读取的每一行都比原始的1个字节缩短了\ r \ n。

为防止此类转换,请使用“二进制”模式,方法是添加“b”模式修改器,例如“RB”。

inputFile = fopen("example.txt", "rb")

https://docs.microsoft.com/en-us/cpp/c-runtime-library/reference/fopen-wfopen?view=vs-2019

在文本模式下,回车换行组合在输入时转换为单行换行,换行符转换为输出上的回车换行组合。

while ((tmpChar = fgetc(inputFile)) != EOF)
{
    strPtr[counter] = tmpChar;
    counter++;
    if (counter == fileSize)
        printf("OK!");
}

此外,此循环(假设文件不包含任何NULL值)将不会终止您的字符串。如果你以后以预期的方式使用strPtr(例如printfstrcmp等),它将读取超过有效范围。

如果你想要一个null终止符,你需要在之后添加一个。为此,您还需要确保分配了一个额外的字节。

realloc(strPtr, (fileSize + 1) * sizeof(char));
while (...
strPtr[counter] = '\0'; // Add null terminator at end.

要处理可能包含空值的文件/字符串,您根本不能使用空终止字符串(例如,使用大小而不是memcmpstrcmp)。

© www.soinside.com 2019 - 2024. All rights reserved.