bash:逐行读取文件,然后sed追加

时间:2013-03-01 15:54:58

标签: bash sed while-loop

我有一个文本文件,可以有X个字段,每个字段用逗号分隔。在我的脚本中,我逐行阅读,检查在该行上填充了多少字段,并确定我需要在该行的末尾追加多少逗号来表示所有字段。例如,文件如下所示:

Address,nbItems,item1,item2,item3,item4,item5,item6,item7    
2325988023,7,1,2,3,4,5,6,7
2327036284,5,1,2,3,4,5
2326168436,4,1,2,3,4

应该成为这个:

Address,nbItems,item1,item2,item3,item4,item5,item6,item7
2325988023,7,1,2,3,4,5,6,7
2327036284,5,1,2,3,4,5,,
2326168436,4,1,2,3,4,,,

我的下面的脚本有效,但看起来非常低效。它是逐行阅读在大文件上有困难吗?导致经济放缓的是它吗?更好的方法吗?

#!/bin/bash

lineNum=0
numFields=`head -1 File.txt | egrep -o "," | wc -l`

cat File.txt | while read LINE
do
        lineNum=`expr 1 + $lineNum`
        num=`echo $LINE | egrep -o "," | wc -l`
        needed=$(( numFields - num ))
        for (( i=0 ; i < $needed ; i++ ))
        do
                sed -i "${lineNum}s/$/,/" File.txt
        done
done

2 个答案:

答案 0 :(得分:11)

这种类型的事情通常最好用awk之类的语言来完成,例如:

awk 'NR==1{n=NF}{$n=$n}1' FS=, OFS=, file

答案 1 :(得分:0)

这是一个完整的bash解决方案。

(
    IFS=","
    read hdrLine
    echo "$hdrLine"
    read -a header <<< "$hdrLine"
    numFields="${#header[@]}"

    while read -a line; do
        pad=${#line[@]}
        while (( pad < numFields )); do
            line[pad++]=
        done
        echo "${line[*]}"
    done
) < File.txt > newFile.txt
mv newFile.txt File.txt

awk解决方案要好得多;这最好被视为bash演示。