在 shell 中将 N 连续行组合在一起?

在 shell 中将 N 连续行组合在一起?

假设我有一个这种格式的文本文件

field1a
field2a
field3a
field1b
field2b
field3b

我想组合 3 个(或一般情况下 N 个)连续行,我将如何使用sedbash shell 中的其他命令行实用程序来完成此操作?

预期产出

field1a:field2a:field3a
field1b:field2b:field3b

答案1

 paste -sd '::\n' file

​​​​​​​ 其中 的行fileself- pasted,其自身依次以::d换行符作为分隔符,或者:

 <file paste -d : - - -

我们将pastestdin、stdin 和 stdin 行:作为delimiter,stdin 在 上打开file

或者:

 awk '{ORS=NR%3?":":"\n";print}' < file

其中O输出RecordS分隔符是换行符或者:取决于Record(行)N编号是否是3的倍数。

(请注意,如果输入中的记录数不是 3 的倍数,则这些方法的行为会有所不同)。

答案2

对于输出格式,您可以使用printf

IFS='
'       # split on sequences of newline characters
set -f # disable globbing
printf "%s:%s:%s\n" $(cat file)

(请注意,它会跳过空行)。

或者sed(如果你愿意的话)

sed '$!N;$!N;s/\n/:/g' file

答案3

sed

sed '$!N;$!N;y/\n/:/'

​​​​​​​​虽然我猜这比N 行比应有的情况要多。如果您想要的行数始终位于字段的末尾,如下所示:

sed '$q;N;/1.$/!s/\(..*\)\(\n\)/\2\1:/;//P;D
' <<\INPUT 
field1a
field1b
field2b
field1c
INPUT

输出

field1a
field1b:field2b
field1c

...它将堆叠以 then 任何单个字符结尾的行,1直到遇到另一个也以1then 结尾的行。

它适用于任意数量的出现字段,但您可能想做......

sed '.../[^0-9]1.$/!...'

...如果您输入多位数。

答案4

如果我只有几百行或更少,或者每组的字段数量不同,那么 vi 对我来说效果很好。

在 vi 中,如果我想加入当前和后续 2 行(总共 3 行文本),那么...

    3J

此时,我的光标位于连接线上,因此我进入下一条......

    j

我使用点对当前行进行相同的修改...

    .

然后再次 ...

    j
    .

哎呀!最后一组有 4 行,而不是 3 行。我撤消了最新的修改...

    u

然后再做一次,这次......

    4J

下一个! ...

    j

……等等。

请注意,如果您打算为 3.6 亿字段的数据库负载执行此操作,或者如果您的连续字段通常为 3 个,其中几组为 4 个,少数一组可能为 5 个或 6 个,那么您可能需要忍受神秘的语法,让自己脱离循环,逐步调节数据,也许编写一个程序来测试它并警告您错误。

但如果这是一项小型一次性工作,那么我只需忍受几分钟的单调乏味并使用 vi 即可。

相关内容