在Linux中使用命令行将xlsx转换为csv

370

我正在寻找在Linux上将xlsx文件转换为csv文件的方法。

由于我需要处理数百万行数据,因此我不想使用PHP / Perl或类似的东西,我需要一个快速的解决方案。我在Ubuntu仓库中找到了一个叫做xls2csv的程序,但它只能转换xls(Office 2003)文件(我目前在使用),但我需要支持更新的Excel文件。

有什么好的建议吗?


11
认为使用脚本语言实现的任何东西在本质上都会变得很慢似乎有些误导人,特别是由于这些语言中有趣的库往往具有用C编写的后端。 - Charles Duffy
2
Excel以前只能处理65536行数据,现在可以处理1048576行(http://support.microsoft.com/kb/120596)。如果要处理数百万行数据,那将会很困难。只是说一下... - Pavel Veller
1
@Pavel 可能分布在多个文件中。 - Charles Duffy
2
个人而言,我会使用Python的xlsv库来完成这个任务,但由于脚本化方法被排除在答案之外... 耸肩。(如果编程工具被排除在答案之外,那这怎么算是一个编程问题呢?) - Charles Duffy
1
@CharlesDuffy,我目前正在使用一个PHP库来完成这个任务,而xls2csv只需要1秒钟,而PHP却需要10分钟。真的是这样。 - user1390150
显示剩余3条评论
12个回答

336

Gnumeric电子表格应用程序附带了一个名为ssconvert的命令行实用程序,可以在各种电子表格格式之间进行转换:

$ ssconvert Book1.xlsx newfile.csv

Using exporter Gnumeric_stf:stf_csv

$ cat newfile.csv

Foo,Bar,Baz
1,2,3
123.6,7.89,
2012/05/14,,
The,last,Line

在Ubuntu上安装:

apt-get install gnumeric

在 Mac 上安装:

brew install gnumeric

25
将电子表格转换为另一种格式最便捷的方式是什么?结合使用Bash脚本可以批量处理多个文件。for f in *.csv; do ssconvert "$f" "${f%.csv}.xlsx"; done虽然LibreOffice方法可能处理其他格式,但我无法使其正常工作(即使使用--headless参数,它也只会每次打开一个空文件)。 - sleblanc
9
@sebleblanc 这并不是完全无忧无虑的。如果你在一个无头服务器上进行安装,由于依赖项的数量,安装过程很麻烦。到目前为止,需要安装 gcc、intltool、zlib-devel、GTK... 而 GTK 需要 glib、atk、pango、cairo、cairo-object、gdk-pixbuf-2.0 等依赖项。 - andrewtweber
15
我成功地通过 apt-get install gnumeric --no-install-recommends 在一个无头的 Debian 服务器上安装了它。唯一的缺点是,运行时会触发很多警告信息 **GConf-WARNING : Client failed to connect to the D-BUS daemon。使用简单的命令 ssconvert oldfile.xlsx newfile.csv > /dev/null 2>&1 就可以解决问题。 - Benjamin Delichere
12
如需将内容写入CSV文件,您可能需要使用-S标志以将多个工作表写入不同的文件中,这样每个工作表都可以单独保存为一个文件。 - Ed Avis
7
分隔符选项仅适用于文本文件导出类型。您可以使用以下命令将其输出到标准输出:ssconvert -O "separator=;" -T Gnumeric_stf:stf_assistant file.xlsx fd://1 - exic
显示剩余11条评论

182

你可以使用LibreOffice来完成此操作:

libreoffice --headless --convert-to csv $filename --outdir $outdir

由于原因不明,您可能需要使用sudo来运行此命令。您可以通过将以下行添加到sudoers文件中,在不需要密码的情况下使LibreOffice能够使用sudo:

%sudo ALL=(ALL) NOPASSWD: /usr/bin/soffice
users ALL=(ALL) NOPASSWD: libreoffice

38
我应该如何告诉LibreOffice我想要第二张表格? - dmeu
35
允许所有人无需密码将sudo授权给libreoffice是在拆开一个潘多拉魔盒。请注意后果,包括在多用户平台上获取root权限的可能性。 - Interarticle
7
这个对我有用(不需要sudo权限)。我的版本是:libreoffice-calc-3.6.7.2-4.fc18.x86_64。 - Brad Hein
8
/Applications/LibreOffice.app/Contents/MacOS/soffice --headless --convert-to csv $filename 在我的苹果电脑上正常运行。 - Nobu
16
要将文本转换为UTF-8编码,并保留非ASCII字符,请改用--convert-to "csv:Text - txt - csv (StarCalc):44,34,76,1,1/1"命令。有关详细信息,请参阅OpenOffice Wiki - Aryeh Leib Taurog
显示剩余10条评论

181
如果您已经有桌面环境,那么我相信 GnumericLibreOffice 都可以很好地工作,但在无头服务器上(例如任何基于云的环境),它们需要安装数十个依赖项。
我找到了这个 Python 替代品:xlsx2csv
easy_install xlsx2csv
xlsx2csv file.xlsx > newfile.csv

我只需要两秒钟安装,就能完美运行。

如果您有多个表格,您可以一次性导出所有表格,或者逐个导出:

xlsx2csv file.xlsx --all > all.csv
xlsx2csv file.xlsx --all -p '' > all-no-delimiter.csv
xlsx2csv file.xlsx -s 1 > sheet1.csv

他还链接了几个用Bash、Python、Ruby和Java编写的替代方案。

2
对我来说运行得非常好,使用 -s 选项允许将每个工作表提取到单独的文件中——在这种情况下,LibreOffice 无法处理工作表的大小,但 xlsx2csv 没有问题。 - Soren
谢谢!在Ubuntu中非常方便。 - zhuguowei
12
在Debian和Ubuntu中有xlsx2csv软件包,因此您无需通过easy_install手动安装它,而可以使用软件包管理器。 - josch
1
在MacOS上,您需要使用“sudo easy_install xlsx2csv”。 - Frank Hintsch
2
我不知道xlsx2csv有多健壮或功能完整,但它似乎正在积极维护,并且与通过Homebrew在macOS上安装Gnumeric(涉及30多个依赖项)和LibreOffice(几百MB的下载)相比,xlsx2csv没有任何依赖关系,只有50 KB,并且对于我的用例(将PaddleOCR的输出转换为csv)完美地工作。您可以使用pip install xlsx2csv进行安装,也可以从Repository下载最新的release,然后运行xlsx2csv.py - Stefan Schmidt
显示剩余3条评论

61

2
这应该是最佳答案。 - greenie-beans
2
安装csvkit,然后完成。 - WestCoastProjects

50
在Bash中,我使用了这个LibreOffice命令(可执行文件libreoffice)来转换当前目录下所有的.xlsx文件:

在Bash中,我使用了这个LibreOffice命令(可执行文件libreoffice)来转换当前目录下所有的.xlsx文件:

for i  in *.xlsx; do  libreoffice --headless --convert-to csv "$i" ; done

在执行之前请关闭所有已打开的LibreOffice实例,否则它将默默失败。

该命令会处理文件名中的空格。

我几年后再次尝试,但它不起作用。这个问题提供了一些提示,但最快的解决方法是以root身份运行(或者运行sudo libreoffice)。它不够优雅,但很快。

在Windows中使用命令scalc.exe


13
在尝试此操作之前,请确保关闭所有的OpenOffice窗口,否则它将会在静默状态下失败。 - tacone
此外,在Windows上,命令是“scalc.exe”,而不是“libreoffice”。在当前稳定的LO版本上,对我有效。 - AronVanAmmers
1
就我个人而言,这在Ubuntu上现在对我有效。 - oma
注意:仅导出第一页。 - e-info128

14

另一个选项是使用R通过一个小的Bash包装器来方便地使用:

xlsx2txt(){
echo '
require(xlsx)
write.table(read.xlsx2(commandArgs(TRUE)[1], 1), stdout(), quote=F, row.names=FALSE, col.names=T, sep="\t")
' | Rscript --vanilla - $1 2>/dev/null
}

xlsx2txt file.xlsx > file.txt

9
如果 .xlsx 文件有很多工作表,可以使用 -s 标志来获取所需的工作表。例如:
xlsx2csv "my_file.xlsx" -s 2 second_sheet.csv

second_sheet.csv 包含 my_file.xlsx 中第二个工作表的数据。


7
使用自带名为 ssconvert 的命令行实用程序的电子表格应用程序 Gnumeric 真的非常简单。
find . -name '*.xlsx' -exec ssconvert -T Gnumeric_stf:stf_csv {} \;

完成了!


非常有用,感谢Pascal-Louis Perez先生。 - Karthickkumar Nagaraj
1
上述命令“ssconvert”只能转换65536行,但我有更多的行数缺失,你能帮我吗? - Karthickkumar Nagaraj

4
如果您可以运行Java命令行,则可以使用Apache POI HSSF的Excel Extractor来完成。它有一个main方法,称为命令行提取器。这个似乎只是把所有东西都倾倒出来了。他们指出这个将转换为CSV的示例。在运行之前,您必须编译它,但它也有一个main方法,因此您不需要做太多的编码以使其工作。

另一个可能可行但需要在另一端进行一些工作的选择是将您的Excel文件以Excel XML数据或XML电子表格的形式发送给您,无论微软现在称呼该格式为什么。这将为您打开一个全新的机会世界,让您按照自己的方式对其进行切割和挖掘。


1
你知道这个是否也支持 .xlsx 吗? - dimroc

4

您可以使用可执行文件 libreoffice 将您的 .xlsx 文件转换为 csv:

libreoffice --headless --convert-to csv ABC.xlsx

--headless参数表示我们不需要GUI界面。


这个答案已经在8年前给出了。 - moopet

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接