在C中编写我自己的'fgets()'版本

tad*_*123 0 c file fgets

我想创建自己的函数版本fgets().我试图这样做,但遇到了一些问题.请告诉我哪里出错了.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

char *my_fgets(char my_string[], int bytes, const char *filename) {
    int i = 0;
    FILE *fp;

    if ((fp = fopen(filename, "wb")) == NULL) {
        fprintf(stderr,"Couldn't open the file");
        return NULL;
    }

    while (sizeof(my_string) < bytes || my_string[i] != '\n')
        my_string[i++] = getc(fp);

    my_string[i] = '\0';        //adding NULL character at the end

    /*   using pointers
    char *p;
    for (p = array; p < array + bytes; p++)
        *p = getc(fp);    
    *p = '\0';  */    

    fclose(fp);
    return my_string;    
}

int main() {
    char my_string[15];
    int n;
    char *p;

    p = my_fgets(my_string, sizeof(my_string), stdin);    

    printf("\n%s", my_string);
    printf("\n%s", p);

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

我的输出没有运行,它立即崩溃.任何帮助,将不胜感激.

chq*_*lie 5

您执行的fgets()有许多重大问题:

  • 原型是不正确的:最后一个参数应该是流指针(FILE *),而不是文件名(const char *).你调用你的函数stdin,这确实是一个流而不是文件名.编译器应该为这个错误发出警告.恕我直言这个警告应该是一个错误.启用所有编译器警告,不要忽略它们:gcc -Wall -W -Werror.

  • 要打开一个文件作为文本阅读,你应该使用一个模式字符串"r",而不是"wb"截断文件,但由于函数应该收到一个FILE *,这是一个没有实际意义的点.

  • 测试输入while (sizeof(my_string) < bytes || my_string[i] != '\n')是错误的,原因有很多:你应该i与数组大小进行比较,而不是sizeof(my_string)一个常量,一个指针的大小,你应该比较从文件读取的字节,而不是my_string[i]你还没有存储的字节.此外,您应该使用logical和operator(&&)来组合这些测试,而不是逻辑或(||).

  • 最终'\n'应该存储到目标数组中.

  • 您不会NULL在文件末尾返回.

  • 您不处理零缓冲区大小的特殊情况.

这是一个改进版本:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

char *my_fgets(char my_string[], int bytes, FILE *fp) {
    int c, i = 0;

    if (bytes <= 0)
        return my_string;

    while (i < bytes - 1 && ((c = getc(fp)) != EOF) {
        my_string[i++] = c;
        if (c == '\n')
            break;
    }
    my_string[i] = '\0'; //adding NUL character at the end

    if (i > 0) {
        return my_string;
    } else {
        return NULL;  // no character read at end of file
    }
}

int main(void) {
    char my_string[15];
    int n;
    char *p;

    p = my_fgets(my_string, sizeof(my_string), stdin);

    printf("%s\n", my_string);
    printf("%s\n", p);

    return 0;
}
Run Code Online (Sandbox Code Playgroud)