通过 sed 替换多个值的正则表达式模式

通过 sed 替换多个值的正则表达式模式

我有一个脚本,我需要在其中解析本地主机的 IP 地址,并将第二个八位字节替换为不同的值,但替换的值取决于当前的值......

例如,如果 IP 是10.10.100.6,那么我需要的结果是10.20.100.6,如果 IP 是10.20.100.6,那么我需要的结果是10.10.100.6

我尝试了以下方法:

nmcli con show eno16777984 | grep -E '^ipv4.address' | awk -F"/|[[:space:]]+" '{print $2}' | sed -e 's/^10\.10\./10.20./; s/^10\.20\./10\.10\./'

我遇到的问题是,sed替换是按照命令中设置的顺序发生的。所以结果总是10.10....

有没有办法让 sed 仅在当前值与模式匹配时才替换值?

谢谢!

聚苯乙烯这需要是简短的一行代码,因为这行代码将通过在几个地方替换来执行,而执行此操作的人的经验/知识都有限,因此只需从文档中复制和粘贴即可。

更新

我最终找到了如何通过以下方式做到这一点awk

nmcli con show eno16777984 | grep -E '^ipv4.address' | awk -F"/|[[:space:]]+" '{print $2}' | awk -F. '{print $1"."($2 == "10" ? "20" : "10")"."$3"."$4}'

但下面有一些很好且简单的答案展示了如何做到这一点sed

答案1

只需添加t;

sed -e 's/^10\.10\./10.20./;t;s/^10\.20\./10\.10\./'

它会在成功时分支到最后。但你确实应该将所有这些 grep、awk、sed 合并到一个 awk 中。

答案2

要交换两个字符串,请使用临时的第三个字符串,该字符串不会以其他方式改回。

sed -e 's/^10\.10\./10.foo./g; s/^10\.20\./10.10./g; s/^10\.foo\./10.20./g'

答案3

无需在此处通过管道grepsed进入awkawk进入awkawk可以一次性完成这一切:

nmcli con show eno16777984 | 
  awk -F"/|[[:space:]]+" '
    /^ipv4.address/ {
      if ($2 ~ /^10\.10/) {
        sub(/10\.10/,"10.20",$2);
      } else if ($2 ~ /^10\.20/) {
        sub(/10\.20/,"10.10",$2);
      };
    };

    1' 

在以 开头的行中ipv4.address,如果第二个字段以 开头10.10,则将其替换为10.20;如果以 开头10.20,则将其替换为10.10。打印所有行,无论它们是否被修改。 (这1是一个 awk 快捷方式 - 1 始终评估为 true,默认操作是打印...该行有效if true then print the current line)。

相关内容