繁体   English   中英

CSV 在 Python 添加一个额外的回车,在 Windows

[英]CSV in Python adding an extra carriage return, on Windows

import csv

with open('test.csv', 'w') as outfile:
    writer = csv.writer(outfile, delimiter=',', quoting=csv.QUOTE_MINIMAL)
    writer.writerow(['hi', 'dude'])
    writer.writerow(['hi2', 'dude2'])

上面的代码生成一个文件test.csv ,每行都有一个额外的\r ,如下所示:

hi,dude\r\r\nhi2,dude2\r\r\n

而不是预期的

hi,dude\r\nhi2,dude2\r\n

为什么会发生这种情况,或者这实际上是期望的行为?

蟒蛇3:

官方csv文档建议在所有平台上使用newline='' open文件以禁用通用换行符翻译

with open('output.csv', 'w', newline='', encoding='utf-8') as f:
    writer = csv.writer(f)
    ...

CSV lineterminator使用方言lineterminator终止每一行,对于所有平台上的默认excel方言,这是'\\r\\n' ,因为这是RFC 4180推荐的。


蟒蛇2:

在 Windows 上,在将文件传递给csv.readercsv.writer之前,始终以二进制模式( "rb""wb" )打开文件。

尽管该文件是文本文件,但所涉及的库将 CSV 视为二进制格式, \\r\\n分隔记录。 如果该分隔符以文本模式编写,则 Python 运行时会将\\n替换为\\r\\n ,因此在文件中观察到\\r\\r\\n

请参阅此先前的答案

虽然@john-machin给出了一个很好的答案,但它并不总是最好的方法。 例如,除非您将所有输入编码到 CSV 编写器,否则它不适用于 Python 3。 此外,如果脚本想要使用 sys.stdout 作为流,它也没有解决这个问题。

我建议在创建编写器时设置 'lineterminator' 属性:

import csv
import sys

doc = csv.writer(sys.stdout, lineterminator='\n')
doc.writerow('abc')
doc.writerow(range(3))

该示例适用于 Python 2 和 Python 3,并且不会产生不需要的换行符。 但是请注意,它可能会产生不需要的换行符(在 Unix 操作系统上省略 LF 字符)。

然而,在大多数情况下,我认为这种行为比将所有 CSV 视为二进制格式更可取,更自然。 我提供此答案作为供您考虑的替代方案。

在 Python 3 中(我没有在 Python 2 中尝试过),你也可以简单地做

with open('output.csv','w',newline='') as f:
    writer=csv.writer(f)
    writer.writerow(mystuff)
    ...

根据文档

在文档的脚注中有更多关于此的信息:

如果未指定 newline='',则不会正确解释嵌入在引用字段中的换行符,并且在写入时使用 \\r\\n linendings 的平台上将添加额外的 \\r。 指定 newline='' 应该始终是安全的,因为 csv 模块执行自己的(通用)换行处理。

您可以在 csv writer 命令中引入lineterminator='\\n'参数。

import csv
delimiter='\t'
with open('tmp.csv', '+w', encoding='utf-8') as stream:
    writer = csv.writer(stream, delimiter=delimiter, quoting=csv.QUOTE_NONE, quotechar='',  lineterminator='\n')
    writer.writerow(['A1' , 'B1', 'C1'])
    writer.writerow(['A2' , 'B2', 'C2'])
    writer.writerow(['A3' , 'B3', 'C3'])

我不确定为什么会发生这种情况,但是将文件模式从“ w”更改为“ wb”可以解决此问题。 有关更多详细信息,请参见我对“ 如何删除^ M ”的回答。

你必须添加属性 newline="\\n" 来打开这样的函数:

with open('file.csv','w',newline="\n") as out:
    csv_out = csv.writer(out, delimiter =';')

请注意,如果您使用 DictWriter,您将有一个来自 open 函数的新行和来自 writerow 函数的新行。 您可以在 open 函数中使用 newline='' 来删除额外的换行符。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM