CSV文件中DoubleDouble引号中的逗号

时间:2014-01-08 08:33:03

标签: python csv

我有一个像示例中给出的字符串:

data = '02 JAN 2014,FEB 2014,A,1.00,,,""1,235.100000"",""1,230.00"",Column'

如何使用python的csv模块解析此字符串?

data = StringIO.StringIO(data) 
reader = csv.reader(data, quoting=csv.QUOTE_NONE)

它将字符串""1,235.10000""分隔为两列:'""1''235.1000""'

如何修复此问题并安排模块如果用双引号将其分开?

3 个答案:

答案 0 :(得分:2)

我不确定这是否足够好,但是:

>>> import csv
>>> data = '02 JAN 2014,FEB 2014,A,1.00,,,""1,235.100000"",""1,230.00"",Column'
>>> reader = csv.reader([data.replace('""', '|')], quotechar='|')
>>> next(reader)
['02 JAN 2014', 'FEB 2014', 'A', '1.00', '', '', '1,235.100000', '1,230.00', 'Column']

您可以使用StringIO或其他任何内容,但传入列表会使示例代码更简单:)。如果你实际上有一个文件对象,你甚至可以使用一个简单的生成器来转换行,然后再将它们提供给你的阅读器:

def transform(file):
   for line in file:
       yield line.replace('""', '|')

with open('foo') as fin:
    reader = csv.reader(transform(fin), quotechar='|')
    ...

transform可以变得像你想的那样复杂 - 例如如果由于某种原因需要保留引号。

答案 1 :(得分:1)

处理此问题的最佳方法是修复输入文件;列的开头处的两个引号字符被视为带引号的空值,并在正常的引用规则生效时从输入中删除。最后的双引号被视为价值的一部分。

您可以通过对每一行进行后处理来修复事后的值:

def rejoin_quoted(row):
    new_row = []
    it = iter(row)
    for col in it:
         new_row.append(col)
         if col.startswith('""'):
             new_col = [col]
             for col in it:
                 new_col.append(col)
                 if col.endswith('""'):
                     new_row[-1] = ','.join(new_col).strip('"')
                     break
    return new_row

演示:

>>> row = ['02 JAN 2014', 'FEB 2014', 'A', '1.00', '', '', '""1', '235.100000""', '""1', '230.00""', 'Column']
>>> rejoin_quoted(row)
['02 JAN 2014', 'FEB 2014', 'A', '1.00', '', '', '1,235.100000', '1,230.00', 'Column']

答案 2 :(得分:1)

这样做的一种方法是稍微修改数据,以便明确指定quote-char和转义字符:

data = '02 JAN 2014,FEB 2014,A,1.00,,,"\"1,235.100000\"","\"1,230.00\"",Column'
parsed = csv.reader(data, delimiter=',', quotechar='"', escapechar='\\')