简体   繁体   English

如何为结构数组分配内存,然后将该数组传递给函数,该函数将在C中填充该数组

[英]How to allocate memory for an array of structs, then pass that array to a function, which populates the array in C

I'm writing a program where I am trying to allocate memory for an array of structs in the main then pass the array to a function which reads data in from a file, creates the structs and populates the array with the structs created. 我正在编写一个程序,试图在主程序中为结构数组分配内存,然后将该数组传递给一个函数,该函数从文件中读取数据,创建结构并使用创建的结构填充数组。

For some reason this piece of code is only allocating enough memory for 7 elements in the array; 由于某种原因,这段代码只能为数组中的7个元素分配足够的内存。

int assets_size = count_lines("rescue_assets.txt");
asset *assets;
assets = (asset*)malloc(sizeof(asset)*assets_size);

The amount of lines in the file are 37 and the count_lines method works, as it is tested in the main. 文件中的行数为37,count_lines方法有效,因为它已在主程序中进行了测试。

Below is the complete code for the main; 以下是主要代码的完整代码;

int main(int argc, char** argv) {
    int i;
    int assets_size = count_lines("rescue_assets.txt");
    asset *assets;
    assets = (asset*)malloc(sizeof(asset)*assets_size);
    ship ships[100];

    printf("%d\n", assets_size);

    printf("%lu\n", sizeof(assets));

    read_data(assets, ships);

    printf("%lu\n", sizeof(assets));

    for (i=0; i<sizeof(assets)-1; i++) {
        printf("%d\n", assets[i].deployment_time);
    }
    free(assets);
    return (EXIT_SUCCESS);
}

Below is the relevant code for the function read_data; 以下是函数read_data的相关代码;

void read_data(asset *assets, ship ships[]) {
int max_assets;
int max_ships;
FILE *asset_file_ptr;
FILE *ship_file_ptr;
int count = 0;
int file_max = 100;
char asset_file[file_max];
char ship_file[file_max];

asset_file_ptr = fopen("rescue_assets.txt", "r");

if (asset_file_ptr == NULL) {
   printf("The asset file could not be opened."); 
   exit(0);       
}
else {
    char callsign[file_max];
    char type;
    char placename[file_max];
    double base_longitude;
    double base_latitude;
    double speed;
    int deployment_time;
    int service_time; 

    while (fscanf(asset_file_ptr, "%s %c %s %lf %lf %lf %d %d", callsign, &type,    placename, &base_longitude, &base_latitude, &speed, &deployment_time, &service_time)!= EOF) {
        asset* new_asset = malloc(sizeof(asset));
        new_asset->callsign = callsign;
        new_asset->type = type;
        new_asset->placename = placename;
        new_asset->base_longitude = base_longitude;
        new_asset->base_latitude = base_latitude;
        new_asset->speed = speed;
        new_asset->deployment_time = deployment_time;
        new_asset->service_time = service_time;

        assets[count] = *new_asset;
        count++;
    }
}
fclose(asset_file_ptr);

}

Here is the output I get from running the main; 这是我从运行主程序得到的输出;

37 8 8 600 180 180 818 180 600 37 8 8 600 180 180 818 180 600

the program first prints out the assets_size, which is 37. then it prints out the size of the assets array, which should be 37, but is 8. same again. 程序首先打印出asset_size,为37。然后,打印出资产数组的大小,应为37,但应为8。 It then prints out the deployment time of all the assets that have been populated in to the array, which is only 7. 然后,打印出已填充到阵列中的所有资产的部署时间,仅为7。

Please can someone tell me where I'm going wrong? 请有人能告诉我我要去哪里错了吗?

The problem is in your for loop in main to print the deployment times, sizeof(assets) does not give you the length of the array, there is no way to get the length of an array only pointed to by a simple pointer. 问题出在您的for循环中,主要用于显示部署时间, sizeof(assets)不能给您数组的长度,没有办法获取仅由简单指针指向的数组的长度。 sizeof(assets) gives you the size of a pointer in chars, which is 8 as you're apparently working on a 64 bit platform. sizeof(assets)给出的指针大小为chars,显然是在64位平台上工作,因此为8。 Simply run from 0 up to asset_size . 只需从0运行到asset_size

And why are you mallocing a new struct in read_data for each asset, just write directly into the asset array. 以及为什么要在read_data为每个资产分配一个新结构,而直接将其直接写入资产数组。

In main do: 在主要方面:

for (int i = 0; i < size_assets; ++i)
    printf("%d\n", assets[i].deployment_time);

In read_data do: 在read_data中执行:

asset* asset_p = assets;
while (fscanf(...) != EOF) {
    asset_p->field = data;
    ...
    ++asset_p;
}

or alternatively: 或者:

int i = 0;
while (fscanf(...) != EOF) {
    assets[i].field = data;
    ...
    ++i;
}

or yet alternatively: 或另选地:

for (int i = 0; fscanf(...) != EOF; ++i) {
    assets[i].field = data;
    ...
}

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

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