回 帖 发 新 帖 刷新版面

主题:[讨论]C++读csv文件(用逗号分隔的)到数组

现在有个编程任务,就是用C++读取csv数据文件,要求将读取的数据放到一个数组中,其中csv文件为300多列的整数或小数组成。

由于本人没学过C++,本人也在网上看过一些程序,因不懂C++语言,虽然明白大概的思路,还是不会写程序,所以恳请大牛们能给出程序。

另附一份,我看到的外文的方法http://www.daniweb.com/software-development/cpp/threads/204808/parsing-a-csv-file-separated-by-semicolons,感觉不错。就是不懂C++语言,所以自己还没有办法写出程序来。

希望大牛们能帮个忙啊,非常感激。

回复列表 (共9个回复)

沙发

自个回一下,有大牛在啊?帮忙看下啊,谢谢啊

板凳

http://blog.vckbase.com/bruceteen/archive/2012/08/15/57405.html

若有bug,请report给我,谢谢

3 楼

哦,如果只有“整数或小数”的话,不需要那么复杂,直接读好了

4 楼


谢谢了,不过还是不大懂,没学过C++。
我是需要把这个功能(一段程序)嵌入到现有的C++程序中,读数,然后调用后面的C++生成的dll文件。
这个dll文件还是调用了fortran生产的函数,挺复杂的。我自己是用fortran编程的,这个C++是老师给的程序,我只要往里面潜入程序就行了。
哎,我还是自己去借本C++书看下了。
还是非常感谢!

5 楼

[quote]http://blog.vckbase.com/bruceteen/archive/2012/08/15/57405.html

若有bug,请report给我,谢谢[/quote]

谢谢了,不过还是不大懂,没学过C++。我是需要把这个功能(一段程序)嵌入到现有的C++程序中,读数,然后调用后面的C++生成的dll文件。这个dll文件还是调用了fortran生产的函数,挺复杂的。我自己是用fortran编程的,这个C++是老师给的程序,我只要往里面潜入程序就行了。哎,我还是自己去借本C++书看下了。还是非常感谢!

6 楼

[quote]http://blog.vckbase.com/bruceteen/archive/2012/08/15/57405.html 若有bug,请report给我,谢谢[/quote] 程序中有个错误:应该是csvvalue子程序下,D:\C RD CSV\luntan\11.cpp(93) : eerror C2039: clear : is not a member of basic_string,class std::allocator >。

7 楼

csv数据文件的列数是固定的吗,还是运行时才知道?
csv数据文件的行数是固定的吗,还是运行时才知道?
csv数据文件的每行包含有同样数量的逗号,还是不一定?
也就是会不会出现
1,2,3,4
2,3
5,6,7
还是
1,2,3,4
2,3,,
5,6,7,

8 楼

[quote]csv数据文件的列数是固定的吗,还是运行时才知道? csv数据文件的每行包含有同样数量的逗号,还是不一定? 也就是会不会出现 1,2,3,4 2,3 5,6,7 还是1,2,3,4 2,3,, 5,6,7, [/quote] 就是非常规范的excel表格数据,形如1,2,...,3,4共n多行,保存成csv文件,目前是340列,以后可能后变,但数量确定,运行前就能知道,在编程时可以直接改就可以,如for{ i= 0,i<340,i++},若确定列数为350后,直接将340改为350,不需要设其他选择语句。 程序功能仅是将已知列数的,以逗号分隔的一行数据,保存到数组。 行数是现在没要求,应该是在程序中加个外循环就可以实现了。

9 楼

n不能在读csv之前就知道的话,连动态分配 new double[n][340] 都不行,因此只能用动态数组
算了,我就当你340也不知道
[code=c]
#include <vector>
#include <fstream>
#include <iomanip>
#include <iostream>

bool readfromcsv( const char* filename, std::vector<double>& data, size_t& width )
{
    data.clear();
    width = 0;
    std::ifstream file( filename );
    if( !file )
    {
        std::cerr << "文件读取失败.\n";
        return false;
    }

    size_t c = 0; // 列数
    for( double d; file>>d; )
    {
        data.push_back( d );
        ++c;

        char s; // 数值后的分隔符,是逗号,还是回车
        if( !(file>>std::noskipws>>s) )
            break;

        if( s == ',' )
        {
        }
        else if( s == '\n' )
        {
            if( width == 0 ) // 还未能确定列数
            {
                width = c;
            }
            else if( width != c ) // 跟以前的列数不一致
            {
                size_t r = (data.size()-c)/width+1; // 当前行数
                std::cerr << "error: 行" << r << "长度和上行不一致.\n";
                return false;
            }
            c = 0;
        }
        else
        {
            size_t r = (data.size()-c)/width+1; // 当前行数
            std::cerr << "error: 行" << r << "列" << c << "出现意外字符.\n";
            return false;
        }
    }
    if( width == 0 )
        width = c;
    if( width == 0 )
    {
        std::cerr << "文件内容为空.\n";
        return false;
    }
    if( data.size()%width != 0 )
    {
        size_t r = (data.size()-c)/width; // 当前行数
        std::cerr << "error: 行" << r << "长度和上行不一致.\n";
        return false;
    }

    return true;
}
int main(void)
{
    std::vector<double> data;
    size_t width;
    if( readfromcsv("D:\\sources\\cpp001\\Book1.csv",data,width) )
    {
        size_t height = data.size() / width;

        for( size_t r=0; r<height; ++r )
        {
            for( size_t c=0; c<width-1; ++c )
            {
                std::cout << data[r*width+c] << ',';
            }
            std::cout << data[r*width+width-1] << '\n';
        }
    }

    return 0;
}
[/code]
随手这么一些,你自己检查一下逻辑错误吧

我来回复

您尚未登录,请登录后再回复。点此登录或注册