简体   繁体   English

Function 返回 C 中的字符串数组

[英]Function that returns array of strings in C

I'm new to C and I'm currently working on a project that I need to read a list from a Json file (using json-c library ).我是 C 的新手,我目前正在做一个项目,我需要从 Json 文件中读取列表(使用json-c library )。 So, I created a function that returns an array of string (the list).因此,我创建了一个返回字符串数组(列表)的 function。 I searched and I found out that to return array of string in a function you need to type something like:我进行了搜索,发现要在 function 中返回字符串数组,您需要输入以下内容:

char** readJson(...) {
    ...
}

and in the main:主要是:

int main() {
    ...
    char** list = readJson();
    ...
}

My problem is that when I create my array, in the read function, I don't declare it, I loop through the list items (from the json object) and I add the them in the list.我的问题是,当我创建数组时,在读取的 function 中,我没有声明它,我循环遍历列表项(来自 json 对象)并将它们添加到列表中。 For example, I don't:例如,我不:

char** list = {"...", "..."}

I do:我愿意:

char** list;
for (int i = 0; i < LIST_SIZE; i++) {
    strcpy(list[i], json_object_get_string(json_obj));
}

And when I try to print the list item after strcpy (in for loop) it closes the program.当我尝试在 strcpy (在 for 循环中)之后打印列表项时,它会关闭程序。 So, I tried to create the array like that:所以,我试图创建这样的数组:

char list[LIST_SIZE][MAX_CHAR];

And then return this:然后返回:

char** final = list;
return final;

And it worked.它奏效了。 But , when I am returning the list it gives me a warning in the compiler:但是,当我返回列表时,它会在编译器中给我一个警告:

main.c:66:20: warning: initialization from incompatible pointer type [-Wincompatible-pointer-types] main.c:66:20:警告:从不兼容的指针类型初始化 [-Wincompatible-pointer-types]

And when I try to print the list in main it crashes.当我尝试在 main 中打印列表时,它会崩溃。

Here is the source code.是源代码。 Check it if you want.如果需要,请检查它。

Please, help me.请帮我。

You cannot return an array from a function in C.您不能从 C 中的 function 返回数组。

This is not a big problem, because you can always return a pointer to the first element of your array.这不是一个大问题,因为您总是可以返回指向数组第一个元素的指针。 Anyone who has such a pointer can access the whole array.任何拥有这样一个指针的人都可以访问整个数组。

So here is a simple two step plan.所以这里有一个简单的两步计划。

  1. Have an array.有一个数组。
  2. Have a pointer that points to its first element.有一个指向其第一个元素的指针。

The only problem with that is as follows.唯一的问题如下。 If you return a pointer to something from a function, that something better be alive when the function returns.如果你从 function 返回一个指向某个东西的指针,那么当 function 返回时,这个东西最好还活着。 You do not want pointers to dead things floating around.您不希望指向漂浮的死物的指针。 However, normal variables declared in a function, including arrays, die when the function returns.但是,在 function 中声明的正常变量(包括 arrays)会在 function 返回时消失。 So you need something else.所以你需要别的东西。

One way to overcome this is to make the array static or global variable, instead of normal (automatic) variable in a function.解决此问题的一种方法是创建数组 static 或全局变量,而不是 function 中的普通(自动)变量。 This has limited uses.这用途有限。 Your array must be of a fixed size, and of course all calls to your function will return the same thing each time.您的数组必须是固定大小的,当然,对 function 的所有调用每次都会返回相同的内容。

Another way to overcome this is to allocate the array dynamically using the malloc family of functions.克服这个问题的另一种方法是使用malloc系列函数动态分配数组。

char* list = malloc(sizeof(char*) * number_of_elements_in_list);

list now points to the first element of a dynamically allocated array of char* . list现在指向动态分配的char*数组的第一个元素。

Note that its elements are also pointers, and you need to initialize them correctly.请注意,它的元素也是指针,您需要正确初始化它们。 How?如何? Just read this answer again and apply it to each individual string.只需再次阅读此答案并将其应用于每个单独的字符串。 For example例如

for (int i = 0; i < number_of_elements_in_list; ++i)
    list[i] = read_next_json_string(json_object);

So you make an array available to your caller by returning a pointer to the first element of a dynamically allocated array.因此,您可以通过返回指向动态分配数组的第一个元素的指针来使调用者可以使用数组。 In your case, each element of your array is also a pointer pointing to the first element of a dynamically allocated array.在您的情况下,数组的每个元素也是指向动态分配数组的第一个元素的指针。

After your caller is done with the array, they should free the memory occupied by it.在你的调用者完成数组后,他们应该释放它占用的 memory。 And in your case, also free memory occupied by each individual string — before freeing the main array!在您的情况下,还要释放每个单独的字符串占用的 memory - 在释放主数组之前!

As mentioned in the comments, you cannot simply interchange arrays and pointers.如评论中所述,您不能简单地交换 arrays 和指针。 Based on your use-case, I would suggest using malloc() to dynamically allocate your list variable.根据您的用例,我建议使用malloc()动态分配您的list变量。 Something along the lines of:类似于以下内容:

char **list = malloc(LIST_SIZE * sizeof(char *));
for(int i = 0; i < LIST_SIZE; i++)
    list[i] = malloc(MAX_CHAR * sizeof(char));

Doing so will still allow you to reference specific words/sentences by using list[i] and you can return list as a char ** :这样做仍然允许您使用list[i]引用特定的单词/句子,并且您可以将list作为char **返回:

char **result = list;
return result;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM