每次用不同的字符串替换模式(取自外部文件)

E.C*_*E.C 4 sed awk perl text-processing

我有一个输入:

a
b TOCHANGE
c
d 
e TOCHANGE
Run Code Online (Sandbox Code Playgroud)

我需要使用外部文件更改模式“TOCHANGE”:

line1
line2
...
Run Code Online (Sandbox Code Playgroud)

以便我得到以下输出:

a
b line1    
c
d
e line2
Run Code Online (Sandbox Code Playgroud)

我尝试了以下命令:

while read k ; do sed -i "s/TOCHANGE/$k/g" input ; done < externalfile
Run Code Online (Sandbox Code Playgroud)

但我得到了:

a
b line1    
c
d
e line1
Run Code Online (Sandbox Code Playgroud)

Sté*_*las 6

perl

perl -pi -e 's{TOCHANGE}{chomp ($repl = <STDIN>); $repl}ge' input <externalfile
Run Code Online (Sandbox Code Playgroud)

随着awk,假设TOCHANGE不发生externalfile(或更一般地替换,并不产生新的发生TOCHANGE也可能发生,例如在包含输入TOTOCHANGE FROMTOCHANGEexternalfile包含CHANGEWHATEVER):

POSIXLY_CORRECT=1 PAT=TOCHANGE awk '
  {
    while ($0 ~ ENVIRON["PAT"]) {
      getline repl < "externalfile"
      gsub(/[&\\]/, "\\\\&", repl)
      sub(ENVIRON["PAT"], repl)
    }
    print
  }' < input > input.new
Run Code Online (Sandbox Code Playgroud)

POSIXLY_CORRECT=1GNUawk需要它,否则它对于包含反斜杠字符的替换字符串将无法正常工作)。

请注意,$PAT以上被视为扩展的正则表达式。如果您希望按字面处理(例如PAT='TO\.CHANGE'替换TO.CHANGE字符串),您可能需要转义 ERE 运算符。