使用C/C++读取csv文件的每一行,以逗号分隔,如果某单元格的数据本身含有逗号,这里如何避免分隔出错?
PHPz
PHPz 2017-04-17 11:43:17
0
3
1145

在使用MFC读取csv文件的每一行并按逗号分隔时遇到这样的问题:

csv文件是用逗号作为列分隔符的,我读到csv文件的一行后,也是按照逗号来进行分割的,以便能够把这一行字符串按照原本csv文件中列的形式分割出来。但是当某个单元格的数据本身就带有逗号时(比如有一个单元格是“中国,朝鲜”),而且该逗号也是英文半角的,这个时候我的分隔便出错了,因为这个逗号的存在,原本csv中占10列的一行现在被分割成了11个,该如何解决?


2015/01/21 10:00更新

问题已经解决,今天有空会贴上解决方法和代码,谢谢各位的热心帮助。
只能采纳一个回答,就选kepler84的吧,也非常感谢Chobits提供的方法!

PHPz
PHPz

学习是最好的投资!

全部回覆(3)
大家讲道理

首先這種情況下每一列(或只是帶有逗號的那一列)必須是要有引號來表示「雖然有逗號但只是一列」這個語意的。否則的話這個CSV格式錯誤。

在有引號的情況下,這時你就不能用簡單的split去處理字串了。簡單的方法是掃描字串,並且標記目前字元是不是在引號裡,如果在引號裡,忽略逗號,否則碰到逗號就分割。

當然,更簡單的方法是用已有的csv library。 github上一大把。

刘奇

http://www.codeproject.com/Articles/9258/A-Fast-CSV-Reader

PHPzhong

CSV格式規格

根據csv的格式規格來看,包含逗號的一列資料應該是被雙引號包起來的,這樣就好辦了,只要把被雙引號包含的字串提取出來然後把裡面的逗號替換成別的符號,然後再拼接上原字串中被雙引號包起的字串左邊和右邊的部分就好了。這裡也只保證適用於格式規範的csv文件,不規範的文件不保證成功。

void _analyse_line(CStringW line) {
    // 保存原字符串副本
    CStringW copy_line = line;
    // 获取首个双引号在字符串中的索引
    int fquote_index = line.Find('\"');
    // 如果不存在双引号,可以直接按照逗号分割该字符串
    // 存在双引号的话检查被双引号包起的字符串中是否存在逗号
    if (fquote_index != -1) {
        int lquote_index = 0, _index;
        // 获取最后一个双引号的索引
        while ((_index = line.Find('\"')) != -1) {
            line = CStringW(line.Right(line.GetLength() - _index - 1));
            lquote_index += _index + 1;
        }
        // 双引号包起的字符串的长度
        int len = lquote_index - fquote_index;
        // 首个双引号左边的字符串
        CStringW left = copy_line.Left(fquote_index);
        line = CStringW(copy_line.Right(copy_line.GetLength() - fquote_index));
        // 最后一个双引号右边的字符串
        CStringW right = CStringW(line.Right(line.GetLength() - len));
        // 被双引号包起的字符串
        line = CStringW(line.Left(len));
        // 替换被双引号包起的字符串中的逗号
        line.Replace('\,', '\t');
        // 拼接新的字符串
        line = left + line + right;
    }
    
    vector arr = split(line, ',');
    // 把用'\t'替换过的逗号还原回来
    for (int i = 0; i 

split方法不贴了,实现方法很多。

熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板