C返回char []警告"返回局部变量的地址"

hal*_*010 5 c pointers return compiler-warnings

这是家庭作业的一部分.

我试图在我的方法getLine中读取并返回一行文件.

char *getLine(FILE *input) {
    char line[30];
    if(fgets(line, sizeof(line), input)!=NULL)
    {
        return line;
    }else{
        return NULL;
    }
}
Run Code Online (Sandbox Code Playgroud)

这似乎与我所教的有关指针的工作有关,但是我无法删除警告消息warning: function returns address of local variable [enabled by default].这个警告指的是这条线return line;.我的作业要求编译时没有警告或错误.我不明白我做错了什么.

我发现的大多数帮助建议为文本行提供malloc-ing空间,但是我们还没有在课堂上讨论过这个问题,尽管我已经在另一个类中做了一些.这真的是最好的方法吗?如果是这样,我可以在节目的任何地方免费吗?

Lih*_*ihO 14

char line[30];是具有自动存储持续时间的数组.一旦执行超出函数范围,它所驻留的内存就会被释放,因此返回的指向该内存的指针变为无效(悬空指针).

尝试访问已经解除分配的内存会导致未定义的行为.

您可以动态分配数组并让调用者显式释放它:

char *getLine() {
    char* line = malloc(30);
    ...
    return line;
}

// somewhere:
char* line = getLine();
...
free(line);
Run Code Online (Sandbox Code Playgroud)


hyd*_*yde 5

不使用malloc的替代方案,据我所知,早先的问题没有涵盖:

/* Warning, this function is not re-entrant. It overwrites result of previous call */
char *getLine(FILE *input) {
    static char line[30];
    return fgets(line, sizeof(line), input);
    /* fgets returns NULL on failure, line on success, no need to test it */
}
Run Code Online (Sandbox Code Playgroud)

说明:静态变量函数范围即使在函数返回保留它们的值.只有这样一个变量的一个实例,每次调用该函数时都使用相同的一个(因此不能重入/线程安全).程序启动时会分配静态变量的内存,既不是堆也不是堆栈,而是在运行程序的内存空间中它自己的保留区域.在第一次使用之前,静态变量的值只被初始化一次(上面没有特定的初始化,所以它用0填充,但它也可以有一个初始化器,并且只有在第一次调用函数时才是它的值).

虽然以这种方式使用静态变量可能看起来有点哈克(我同意它是),它仍然也标准C例如所采用的有效模式strtok()功能.它还表明需要一个可重入的版本,正如C标准所具有的那样strtok_r(),使用起来更复杂,因为它有一个额外的参数而不是其中的局部静态变量.