有一个包含重复注释行的文件,例如:
# ScriptAlias /cgi-bin/ "somepath"
# ScriptAlias /cgi-bin/ "otherpath"
我想仅在最后一次出现后添加一行,导致
# ScriptAlias /cgi-bin/ "somepath"
# ScriptAlias /cgi-bin/ "otherpath"
ScriptAlias /cgi-bin/ "mypath"
为此,我正在使用以下命令:
sed -i 's:^(.*ScriptAlias /cgi-bin/.*):1 nScriptAlias /cgi-bin/ "mypath":' file
但这会导致在每次出现后添加我的行,例如:
# ScriptAlias /cgi-bin/ "somepath"
ScriptAlias /cgi-bin/ "mypath"
# ScriptAlias /cgi-bin/ "otherpath"
ScriptAlias /cgi-bin/ "mypath"
如何告诉 sed 仅替换最后一个出现的位置?
编辑:
如果无法使用 sed 解决它(如评论中所述),请提供达到相同结果的替代方案,谢谢。
已编辑:
重复的行可以分开,并且它们之间的其他行,例如
# ScriptAlias /cgi-bin/ "somepath"
# ScriptAlias /cgi-bin/ "otherpath"
# ScriptAlias /cgi-bin/ "another-path"
ScriptAlias /foo/ "just-jump"
# ScriptAlias /cgi-bin/ "that's the last"
使用 tac,以便在第一次看到模式时打印新行:
tac file | awk '/ScriptAlias/ && ! seen {print "new line"; seen=1} {print}' | tac
awk 的替代方案:
awk '/ScriptAlias /cgi-bin//{x=NR} {a[NR]=$0;}END{for(i=1;i<=NR;i++){if(i==x+1)print "$$$here comes new line$$$"; print a[i];}}' file
测试:
kent$ echo "# ScriptAlias /cgi-bin/ "somepath"
fooo
# ScriptAlias /cgi-bin/ "otherpath"
bar
"|awk '/ScriptAlias /cgi-bin//{x=NR} {a[NR]=$0;}END{for(i=1;i<=NR;i++){if(i==x+1)print "$$$here comes new line$$$"; print a[i];}}'
输出:
# ScriptAlias /cgi-bin/ somepath
fooo
# ScriptAlias /cgi-bin/ otherpath
$$$here comes new line$$$
bar
tail -r temp | awk '{line="yourline"}{if($0~/ScriptAlias/&&last==0){print line"n"$0;last=1}else print}' | tail -r
测试如下:
krithika.337> cat temp
# ScriptAlias /cgi-bin/ "somepath"
# ScriptAlias /cgi-bin/ "otherpath"
# ndmxriptAlias /cgi-bin/ "otherpath"
# ScriptAlias /cgi-bin/ "otherpath"
# bdjiptAlias /cgi-bin/ "otherpath"
krithika.338> tail -r temp | awk '{line="yourline"}{if($0~/ScriptAlias/&&last==0){print line"n"$0;last=1}else print}' | tail -r
# ScriptAlias /cgi-bin/ "somepath"
# ScriptAlias /cgi-bin/ "otherpath"
# ndmxriptAlias /cgi-bin/ "otherpath"
# ScriptAlias /cgi-bin/ "otherpath"
yourline
# bdjiptAlias /cgi-bin/ "otherpath"
krithika.339>
这是编辑的任务。
ex input_file << "DONE"
/ScriptAlias /cgi-bin/ "otherpath"
a
ScriptAlias /cgi-bin/ "mypath"
.
:1
/ScriptAlias /cgi-bin/ "another-path"
a
ScriptAlias /cgi-bin/ "just-jump"
.
:x
DONE
在上次出现模式下。
ex input_file << "DONE"
$
?ScriptAlias /cgi-bin/ "otherpath"
a
ScriptAlias /cgi-bin/ "mypath"
.
$
?ScriptAlias /cgi-bin/ "another-path"
a
ScriptAlias /cgi-bin/ "just-jump"
.
:x
DONE