返回char指针数组时编译器抱怨

时间:2013-08-01 00:55:39

标签: c string pointers char

我正在尝试返回一个char指针数组,但编译器似乎不喜欢它。

char*[] get_multiple(int x) {
    char *tmp[x];
    int i;
    for (i=0;i<x;i++)
        tmp[i]=strdup("abc");
    return tmp;
}

编译器出现以下错误:

error: expected identifier or '(' before '[' token 
第1行

知道为什么编译器不喜欢它以及如何修复它? (我知道我也可以从调用者传入一个结构来存储返回指针,但我想避免这样做)

3 个答案:

答案 0 :(得分:2)

请允许我加入@Lidong Guo的回答(引用如下)

  

您不能通过以下方式创建数组:char * tmp[x],因为x已知运行时!

     

使用char **tmp = malloc(x*sizeof(char *));代替

通过查看您的代码,我可以看到您误解了数组标签tmp实际代表的内容或tmp实际位于何处。

在函数中分配变量(或静态大小的数组)时,它存储在当前堆栈框架<堆栈中< / strong>即可。函数返回后,堆栈帧将被销毁/释放,并且不应再次使用/引用该内存!!!

tmp是一个标签,表示tmp数组所在的内存地址。这是在堆栈上,所以当你的函数返回时它不再是一个有效的指针!

请原谅我,如果你已经知道这一点,但根据你的术语判断,我怀疑你可能没有。

在C中你不能将数组分配给其他数组!

int array1[10], array2[10];

// ... Put some values into array 1 ...

array2 = array1; // ILLEGAL! DOES NOT COPY AN ARRAY

同样,如果你返回tmp,你将返回地址,而不是数组,所以如果你将它分配给另一个变量,你应该复制它而不是分配它!

因此C不允许你返回一个数组而你应该返回指针

但即使你将一个指针返回给tmp,你也会遇到麻烦,因为你试图分配它(在堆栈上)所以@Lidong Guo建议你即使在函数返回后,也可以将它分配到它可以存活的堆上。但是,这意味着您需要记住释放内存!

所以使用@Lidong Guo的代码重写你的函数看起来像

char** get_multiple(int x) {
    char **tmp = malloc(x * sizeof(char*));
    int i;
    for (i=0;i<x;i++)
        tmp[i]=strdup("abc");
    return tmp;
}

假设的主人会像这样使用它:

int main()
{
    char** multiple7;

    multiple7 = get_multiple(7);

    // Do some stuff on multiple 7
    free(multiple7[3]);

    // Do some more stuff ...

    // Don't forget to free multiple7 array memory too
    free(multiple7);

    return 0;
}

答案 1 :(得分:1)

您可以使用两种类型作为函数的返回类型:

  1. 功能类型
  2. 数组类型
  3. 您需要做的是声明一个函数,该函数返回指向char或char **指针的指针。您必须分配足够的内存来存储指向字符串的指针 - 因此,如果您需要7个字符串,则必须分配足够的空间来容纳至少7个char *个对象 - 然后您必须为7个字符串中的每个字符串分配空间并将这些分配给刚刚分配的char *。或者,如果此数组中的所有字符串都具有最大长度,则可以声明一个连续的内存块并计算每个字符串的偏移量。

    为了帮助进行内存管理,还可以创建一个free_multiple函数。

    char **get_multiple(size_t max)
    {
        char **multiple = malloc(max * sizeof(*multiple));
        for (size_t i = 0; i < max; i++)
            multiple[i] = malloc(/* determine max length of string including null terminator */);
        return multiple;
    }
    
    void free_multiple(char **multiple, size_t max)
    {
        for (size_t i = 0; i < max; i++)
            free(multiple[i]); /* free individual strings */
        free(multiple); /* free the container as well */
    }
    

答案 2 :(得分:0)

您不能通过以下方式创建数组:char * tmp[x],因为x已知运行时!

使用char **tmp = malloc(x*sizeof(char *));代替