C -将.csv文件阅读2d字符串数组时出现奇怪的问题

t5fffqht  于 2023-03-27  发布在  其他
关注(0)|答案(1)|浏览(96)

我有一个很大的.csv数据文件,我正试图将其读入一个多维数组(.csv文件中的每个值都是一个字符串),但在标记化方面遇到了一些未知的问题。

while (!feof (st))
{
    fgets (row, CHAR, st);
    token = strtok (row, ",");
    
    while (token != NULL)
    {
        for (int row = 0; row < ROWS; row ++)
            for (int col = 0; col < COLS; col ++)
                strcpy (data [row][col], token);
        token = strtok (NULL, ",");
    }
}

它所做的是直到文件结束,它获取.csv文件的下一行,检测分隔每个值的逗号,然后对于该行的每个值,它将其放入数组中的下一个空位置,然后对每一行重复这个过程。
但是,当我测试打印数据数组时,它不是用.csv文件中的数据填充,而是用“1”填充,这是.csv文件中的最后一个值(在文件的最后一行的最后一列中)。除此之外,数组的底部充满了空的空间和垃圾。我甚至不确定这是怎么可能的,因为我从一开始就声明了数组的确切大小。(我还在程序开始时编写了一些代码来清理.csv文件,以从程序底部删除多余的行。)
有人能给我指引正确的方向吗?我觉得我已经很接近了,因为当我打印标记化的值而不是试图将它们放入数组中时,我能够看到正确打印出的所有值。

mgdq6dx1

mgdq6dx11#

你正在阅读一个带有ftok()的标记,然后循环遍历所有的数组元素,将标记复制到每个元素中。所以在最后,它们都包含最后一个标记。你应该只将每个标记复制到单个元素中。

int rownum = 0;
while (fgets (row, CHAR, st))
{
    int colnum = 0;
    token = strtok(row, ",\n");
    
    while (token != NULL)
    {
        strcpy(data [rownum][colnum++], token);
        token = strtok (NULL, ",\n");
    }
    rownum++;
}

其他问题:

  • 不要使用!feof()作为while条件。而是测试fgets()的结果。请参见Why is “while( !feof(file) )” always wrong?
  • fgets()读取的字符串包含换行符。要么先删除它(参见Removing trailing newline character from fgets() input),要么将其包含在strtok()的分隔符字符串中,这样就不会将其复制到数组中。
  • 避免重复使用变量名。从文件中读取的行和数组的索引都使用了row。虽然它们实际上不会干扰代码,因为它们在不同的作用域中,但这会让读者感到困惑。当我重构循环以将int row = 0;移出循环时,它们最终发生冲突,所以我将它们重命名为rownumcolnum

相关问题