我有一个文本文件,每行都有一些定义数量的字段,但它们可能因行而异。我想做的就是在该行字段中的每个值前面添加“=”符号。
例如输入文件
A B C D E
P Q R S T U
L M N O
输出文件
=A =B =C =D =E
=P =Q =R =S =T =U
=L =M =N =O
另外,这只是一个示例,我的文件包含一些字段数超过 20 的行。如何有效地执行此操作。
答案1
假设您的字段包含多个字母,其中 GNU sed
:
sed 's/\</=/g' <<END
foo bar baz
A B C
apple banana cherry
END
=foo =bar =baz
=A =B =C
=apple =banana =cherry
GNU sed 的\<
正则表达式构造是一个零宽度的“单词开头”标记(非单词(或行开头)和单词字符(区域设置中的数字或下划线)之间的过渡)。所以我们要替换每个的开头单词与“=”字符。
(sed 正则表达式参考这里)
答案2
较短的awk
版本:
$ awk 'gsub(/([^ ]+)/,"=&",$0)' file
=A =B =C =D =E
=P =Q =R =S =T =U
=L =M =N =O
解释
我们对每个输入行进行全局替换:
/([^ ]+)/
: 匹配每个字段,因为字段之间用空格分隔,所以这个正则表达式匹配除空格之外的所有内容。"=&"
: 对于每个字段,在=
其前面添加。
&
含义被匹配的字符替换。从man awk
:
gsub(r, s [, t]) For each substring matching the regular expres‐
sion r in the string t, substitute the string
s, and return the number of substitutions. If
t is not supplied, use $0. An & in the
replacement text is replaced with the text that
was actually matched. Use \& to get a literal
&. (This must be typed as "\\&"; see GAWK:
Effective AWK Programming for a fuller discus‐
sion of the rules for &'s and backslashes in
the replacement text of sub(), gsub(), and gen‐
sub().)
更新
对于 @glenn jackman 的回答和评论,我在以下位置添加了等效版本perl
:
$ perl -pe 's/\b(?=\w)/=$&/g' file
=A =B =C =D =E
=P =Q =R =S =T =U
=L =M =N =O
答案3
要在 中执行此操作awk
,您可以使用:
awk '{for (i=1;i<=NF;i++) printf "=%s ",$i;printf "\n"}' filename
循环内部NF
(字段数)变量,打印每个字段,并在前面添加等号并附加空格,然后在打印所有字段后,打印换行符。
答案4
尝试这个简单的 sed 命令,
sed 's/\([A-Za-z]\+\)/=\1/g' file
例子:
$ (echo 'A B C'; echo 'A C D F') | sed 's/\([A-Za-z]\+\)/=\1/g'
=A =B =C
=A =C =D =F
该命令将在,=
之前放置符号。A-Z
a-z
或者
也尝试这个命令,
sed 's/\([ ]\+\)/\1=/g; s/^\(.*\)$/=\1/g' file
例子:
$ (echo 'A B C'; echo 'A C D F') | sed 's/\([ ]\+\)/\1=/g; s/^\(.*\)$/=\1/g'
=A =B =C
=A =C =D =F
此命令将用一个或多个空格加号替换一个或多个空格,=
并且它会放在=
开头。