将CSV转换为TSV

时间:2019-09-19 15:01:18

标签: linux csv sed

如何将此csv文件转换为制表符分隔的文件?

"Country","Percent","Percent of patients","home health","home health agency","friends and family","Surveys","Response"
"Nation","88","85","83","84","78",,

请注意Surverys和Response均为空字符串。

我使用此代码将其转换为选项卡文件-

sed 's/\"\,\"/\"\t\"/g'
sed 's/\,\,/\t""\t/g'

它不会转换最后一列。这是我得到的输出(注意,省略了最后一列)-

"Country"   "Percent"   "Percent of patients"   "home health"   "home health agency"    "friends and family"    "Surveys"   "Response"
"Nation"        "88"    "85"    "83"    "84"    "78"    ""

标题中有8列,而制表符分隔的数据中只有7列,因此缺少最后一列。

更新

我的列名中包含逗号。

3 个答案:

答案 0 :(得分:1)

实际上,您的最后一栏完全没有丢失。您只是看不到它,因为它是一个标签。您可以使用xxd进行检查。

此外,由于所有内容都在单引号内,因此您无需在s中转义逗号和双引号。

sed 's/","/"\t"/g; s/,,/\t""\t/g;' $YOUR_CSV | xxd | tail -1.

这表明最后一行在最后一个引号之后和结尾的换行符之前以制表符(x09)结尾:

00000090: 3834 2209 2237 3822 0922 2209 0a         84"."78".""..

“缺失”是最后一个空值周围的双引号。但是您不需要它们。如果您确实需要这些双引号,则可以将其添加到sed命令中:

s/\t$/\t""/

它将用一行制表符后接2个双引号代替一行末尾的一个制表符。

但是,根据您的数据,这种简单的sed替换当然很容易失败。

例如(如果可见的列不是结尾,则使用-而不是\t

echo '"Nation","88",,,"84","78",,' | sed 's/","/"-"/g; s/,,/-""-/g;'

将输出

"Nation"-"88"-""-,"84"-"78"-""-

(请注意“ 84”前的逗号)

因此,我建议使用专用工具而不是快速的sed行。例如,csvtool适用于大多数发行版(sudo apt install csvtool适用于基于Debian的发行版)。

csvtool -t COMMA -u TAB cat $YOUR_CSV

答案 1 :(得分:0)

我确实将FPATgnu awk一起使用来处理CSV文件

awk -v FPAT='([^,]+)|("[^"]+")' -v OFS='\t' '{$1=$1}1' file
"Country"       "Percent"       "Percent of patients"   "home health"   "home health agency"    "friends and family"    "Surveys"       "Response"
"Nation"        "88"    "85"    "83"    "84"    "78"

不确定最后一栏是什么意思。如果其空,,您将看不到它。

答案 2 :(得分:0)

使用GNU awk。

awk 'BEGIN{FS="\",\""; OFS="\t"} {FS=","; for(i=1; i<=NF; i++) {gsub(/"/,"",$i); $i="\"" $i "\""} print}' file

输出:

"Country"      "Percent"       "Percent of patients"   "home health"   "home health agency"    "friends and family"       "Surveys"       "Response"
"Nation"        "88"    "85"    "83"    "84"    "78"    ""      ""