用Perl打开在Mac Excel中创build的CSV文件
我在下面的Perl代码中遇到了一些麻烦。 我可以打开并读取我手动创build的CSV文件,但如果我尝试打开任何保存为CSV文件的Mac Excel电子表格,下面的代码将其全部读取为一行。
#!/usr/bin/perl use strict; use warnings; open F, "file.csv"; foreach (<F>) { ($first, $second, undef, undef) = split (',', $_); } print "$first : $second\n"; close(F);
总是使用一个专门的模块(如Text::CSV
或Text::CSV_XS
)来达到这个目的,因为在很多情况下, split
不会有帮助(例如,当字段包含一个不是字段分隔符的逗号时,在引号内)。
传统的Macintosh(系统9和以前)使用CR(0x0D,\ r)作为行分隔符。 Mac OS X(基于Unix)使用LF(0x0A,\ n)作为默认行分隔符,因此作为Unix工具的perl脚本可能期望LF,但获得CR。 由于文件中没有行分隔符,因此perl认为只有一行。 如果它有Windows行结尾(CR,LF),你可能会在每行的末尾看到一个不可见的CR。
用0x0A代替0x0D的input快速循环应该能解决你的问题。
我用Excel 2004 for Mac直接遇到了这个问题。 行结尾确实是\r
和IIRC,文本使用MacRoman字符集,而不是您所期望的Latin-1或UTF-8。
所以以及使用Text :: CSV / Text :: CSV_XS和在\r
上拆分的好build议,您将需要使用MacRoman编码打开文件,如下所示:
open my $fh, "<:encoding(MacRoman)", $filename or die "Can't read $filename: $!";
同样,在Windows上读取使用Excel导出的文件时,您可能希望在该代码中使用:encoding(cp1252)
而不是:encoding(MacRoman)
。
不知道关于Mac的Excel,但肯定是Windows版本倾向于将所有值包含在引号中: "like","this"
。 此外,你需要考虑的价值,这将显示"like""this"
( "like""this"
只有一个单一的"
在这个价值)的报价的可能性。
要真正回答你的问题,很可能它使用了你所期望的不同的换行符。 这可能是\r\n
而不是\n
,反之亦然。
正如其他人所怀疑的,你的线路结局可能是怪罪。 在我的基于Linux的系统上有内置的实用程序来改变这些行结束。 mac2unix
(我认为它只是一个包装dos2unix
将读取你的文件,并改变你的行结束,你应该在Linux和Mac上有类似的东西(微软可能不关心你)。
如果你想在Perl中处理这个,看看设置$/
variables设置“inputlogging分隔符”从“\ n”到“\ r”(如果这是正确的结局)。 在读取文件之前,请尝试使用local $/ = "\r"
。 在perldoc perlvar (接近$/
)或perldoc perlport (致力于编写可移植的Perl代码。
PS如果我有这个不正确的一部分让我知道,我不使用Mac,我只是想我知道这个理论
如果你设置了“特殊variables”来处理它换行符\ r,那么你可以一次读一行:$ / =“\ r”; 在这种情况下,perl的mac新行是默认的\ n,但是文件可能使用了\ r。 这build立了Flynn1179和Mark Thalman所说的,但告诉你如何使用while()风格的阅读。