将.csv中的数据读入struct数组

时间:2017-10-31 20:33:19

标签: c arrays csv struct

我想从文本中读取数据。像这样: 格式:难度;问题;问题A ;;问题B;问题C;问题D;答案;类型 例如:

5;匈牙利在哪里?;非洲;亚洲;澳大利亚;欧洲; D;地理

但是我的代码没有存储在数组中。我的代码:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

typedef struct kerdes{
    int  nehezseg;
    char *ker;
    char A;
    char B;
    char C;
    char D;
    char valasz;
    char *kategoria;
} kerdes;

int main() {
    FILE *file = fopen("./kerdes.csv", "r");
    if (file == NULL){
        perror("Nem sikerult megnyitni a fajlt");
    }

    kerdes *kerdessor = NULL;
    char ker_buf[256], kat_buf[256];
    int i = 0, db = 0;
    while(!feof(file)){
        fscanf(file, "%d;%s;%s;%s;%s;%s;%s;%s",
               &kerdessor[i].nehezseg, ker_buf, kerdessor[i].A, kerdessor[i].B,
               kerdessor[i].C, kerdessor[i].D, kerdessor[i].valasz, kat_buf);

        kerdessor[i].ker = (char*) malloc(strlen(ker_buf) * sizeof(char) + 1);
        kerdessor[i].kategoria = (char*) malloc(strlen(kat_buf) * sizeof(char) + 1);

        strcpy(kerdessor[i].ker, ker_buf);
        strcpy(kerdessor[i].kategoria, kat_buf);

        kerdes *ujtomb = malloc(sizeof(kerdes) * (db+1));
        for (i = 0; i < db; ++i)
            ujtomb[i] = kerdessor[i];
        free(kerdessor);

        kerdessor = ujtomb;
        ++db;
    }

    free(kerdessor);
    fclose(file);
    return 0;
}

感谢您的帮助! :)

1 个答案:

答案 0 :(得分:0)

除了评论之外,您还应该查看字符char与字符数组之间的区别。

每一行如下:

"6;Where is Spain?;Africa;Asia;Australia;Europe;H;History"

您的结构应声明为:

typedef struct kerdes {
    int  number;
    char *string1;
    char *A;
    char *B;
    char *C;
    char *D;
    char ch;
    char *stringF;
} kerdes;

而不是fscanf,您可以使用fgets来阅读整行,并使用strtok来划分部分内容:

char line[1024];
while(fgets(line, sizeof(line), fp))
{
    char *token = strtok(line, ";");
    while(token)
    {
        printf("%s\n", token);
        token = strtok(NULL, ";");
    }
}

上面的循环将显示每行中的所有列。我们必须重写此代码,以便将其传输到kerdes数组。

首先我们需要知道数组应该有多大。读取文件一次,找到总行数,这将是数组的大小。

int lines_total = 0;
rewind(file);//make sure we are at the start of file
while(fgets(line, sizeof(line), file)) lines_total++;
//we have reached the end of the line
rewind(file);
kerdes *k = malloc(lines_total * sizeof(k));

在gcc中,您可以声明kerdes k[lines_total];

现在我们可以写信给k。对于每个malloc指针,您仍然需要char*

k[0].string1 = malloc(other_string_length + 1);
strcpy(k[0].string1, other_string);

或者您可以改为使用strdup

int i = -1;
while(fgets(line, sizeof(line), file))
{
    printf("%s\n", line);
    i++;

    k[i].number = 0;
    k[i].string1 = k[i].stringF = k[i].A = k[i].B = k[i].C = k[i].D = 0;
    k[i].ch = 0;

    char *token = strtok(line, ";"); if(!token) continue;
    k[i].number = atoi(token);

    token = strtok(NULL, ";"); if(!token) continue;
    k[i].string1 = strdup(token);

    token = strtok(NULL, ";"); if(!token) continue;
    k[i].A = strdup(token);

    token = strtok(NULL, ";"); if(!token) continue;
    k[i].B = strdup(token);

    token = strtok(NULL, ";"); if(!token) continue;
    k[i].C = strdup(token);

    token = strtok(NULL, ";"); if(!token) continue;
    k[i].D = strdup(token);

    token = strtok(NULL, ";"); if(!token) continue;
    k[i].ch = token[0];

    token = strtok(NULL, "\n"); if(!token) continue;
    k[i].stringF = strdup(token);
}

最后,您必须释放由malloc和所有strdup分配的所有内存