从 main 调用后填充字符串数组的函数不包含第 0 个元素

Function to populate string array doesn't include the 0th element after called from main

我有以下函数,它接受一个指向数组的指针并填充它:

void parse(char *path, char *array[]){

    char *temp = malloc(sizeof(path));
    strcpy(temp, path);

    char *token = strtok(temp, "/");

    int i = 0;
    while(token != NULL){
        array[i++] = token;
        token = strtok(NULL, "/");
    }   
    free(temp);

}

像这样从 main 调用:

...
char *array[3];
path = argv[1];
parse(path, array);
...

然而,当我从它之前的解析函数中打印数组元素时 returns,我得到了正确的输出,即如果路径是 one/two/three/,它将输出:

one
two
three

但是如果我在调用 parse() 后从 main 打印数组元素,输出不包含数组 [0]:

处的元素
two
three

用于打印元素的代码如下:

for (int i = 0; i < 3; i++){
        printf("%s \n", array[i]);
    }

我想我缺少一些与 C 指针或字符串相关的东西,因为我不明白为什么会这样。

编辑:注释掉行 free(temp) 解决了这个问题,但为什么这会特别影响数组的第一项而不是整个数组?

这里

char *temp = malloc(sizeof(path)); 

您正在分配指针的大小。相反

char *temp = malloc(strlen(path)+1);

分配路径指向的字符串的大小(尾部[=14=]+1)。

原因:strcpy(temp, path) 可能需要比指针大小更多的字符,在这种情况下结果是未定义的行为。

此外,strtok returns 指向 temp 的指针,它在函数结束时被释放。因此,再次出现未定义的行为。

所以你最好在 main 中分配一个临时字符串,然后在使用后释放它:在 main()

char *array[3];
char *path = argv[1];
char *temp = malloc(strlen(path)+1);
strcpy(temp, path);

parse(temp, array);

for (int i = 0; i < 3; i++){
     printf("%s \n", array[i]);
}

free(temp);

解析()

void parse(char *path, char *array[]){
    char *token = strtok(path, "/");

    int i = 0;
    while(token != NULL){
         printf("%s\n",token);
         array[i++] = token;
         token = strtok(NULL, "/");
    }   
}

你也可以

  • parse()
  • 中保留 temp 的分配
  • parse()returntemp(不释放它)
  • main() 中,您将该指针存储在变量中 char *tobefree = parse(...);
  • 然后用array
  • 做运算
  • 然后 free(tobefree);