Linux 如何在两个匹配图案之间但在第二个图案之前插入一条线

Linux 如何在两个匹配图案之间但在第二个图案之前插入一条线,linux,awk,sed,Linux,Awk,Sed,我正在尝试将特定ethX设备的dns名称服务器x.x.x.x行添加到/etc/network/interfaces 这是可以更改的,它可能是另一个文件中的另一行 i、 e.将dns名称服务器添加到em1 我想用一些像: sed -i '/^auto em1/,/^auto/ .....' /etc/network/interfaces 目前: auto lo iface lo inet loopback auto em1 iface em1 inet static address 192.16

我正在尝试将特定ethX设备的dns名称服务器x.x.x.x行添加到/etc/network/interfaces 这是可以更改的,它可能是另一个文件中的另一行

i、 e.将dns名称服务器添加到em1 我想用一些像:

sed -i '/^auto em1/,/^auto/ .....' /etc/network/interfaces
目前:

auto lo
iface lo inet loopback
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
我想要的是:

auto lo
iface lo inet loopback
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
dns-nameservers x.x.x.x (<- this line inserted)
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
提前感谢。

谢谢您的救援

$ awk '/^auto em1/       {f=1} 
       /^auto eth1/ && f {print "NEW LINE GOES HERE"; f=0}1' file

auto lo
iface lo inet loopback
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
NEW LINE GOES HERE
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
举例说明注释:如果找到多对开始/结束模式,则匹配将继续在文件之间进行,并循环。比如说

$ awk '/^3/     {f=1} 
       /^6/ && f{print "HERE"; f=0}1' <(seq 5) <(seq 4 7)

1
2
3
4
5
4
5
HERE
6
7
第一个输入文件没有结束模式,即6,但搜索将在第二个文件上继续

如果这不是缩进的行为,请澄清问题。

awk to the rescue

$ awk '/^auto em1/       {f=1} 
       /^auto eth1/ && f {print "NEW LINE GOES HERE"; f=0}1' file

auto lo
iface lo inet loopback
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
NEW LINE GOES HERE
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
举例说明注释:如果找到多对开始/结束模式,则匹配将继续在文件之间进行,并循环。比如说

$ awk '/^3/     {f=1} 
       /^6/ && f{print "HERE"; f=0}1' <(seq 5) <(seq 4 7)

1
2
3
4
5
4
5
HERE
6
7
第一个输入文件没有结束模式,即6,但搜索将在第二个文件上继续


如果这不是缩进行为,请澄清问题。

一种解决方案可以满足您当前和未来的需求,即将与给定设备相关联的每组行保存为一条记录,然后从函数中打印出来,例如:

$ awk '/^auto/{prtDev()} {dev = dev $0 ORS} END{prtDev()}
    function prtDev() {printf "%s", dev; dev=""}' file
auto lo
iface lo inet loopback
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
虽然这看起来只是按原样打印输入文件,但看看调整函数使其在第二台设备的末尾添加一行是多么容易:

$ awk '/^auto/{prtDev()} {dev = dev $0 ORS} END{prtDev()}
    function prtDev() {printf "%s", dev; if (cnt++ == 2) print "dns-nameservers x.x.x.x"; dev=""}' file
auto lo
iface lo inet loopback
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
dns-nameservers x.x.x.x
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
或仅打印设备em1的记录:

$ awk '/^auto/{prtDev()} {dev = dev $0 ORS} END{prtDev()}
    function prtDev() {if (dev ~ / em1 /) printf "%s", dev; dev=""}' file
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1

或在特定网关IP地址上进行匹配,或仅在环回上进行匹配,或在每个设备上选择或操作您要打印的特定行或任何其他内容。

一种解决方案可以满足您当前和未来的需要,即将与给定设备关联的每组行保存为单个记录,然后从函数打印,例如:

$ awk '/^auto/{prtDev()} {dev = dev $0 ORS} END{prtDev()}
    function prtDev() {printf "%s", dev; dev=""}' file
auto lo
iface lo inet loopback
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
虽然这看起来只是按原样打印输入文件,但看看调整函数使其在第二台设备的末尾添加一行是多么容易:

$ awk '/^auto/{prtDev()} {dev = dev $0 ORS} END{prtDev()}
    function prtDev() {printf "%s", dev; if (cnt++ == 2) print "dns-nameservers x.x.x.x"; dev=""}' file
auto lo
iface lo inet loopback
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
dns-nameservers x.x.x.x
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
或仅打印设备em1的记录:

$ awk '/^auto/{prtDev()} {dev = dev $0 ORS} END{prtDev()}
    function prtDev() {if (dev ~ / em1 /) printf "%s", dev; dev=""}' file
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1

或在特定网关IP地址上匹配,或仅在环回上匹配,或在每个设备上选择或操作您要打印的特定行或任何其他内容。

这可能适用于GNU-sed:

sed '/^auto em1/!b;:a;$bb;n;/^auto/!ba;:b;idns-nameservers x.x.x.x' file

遇到自动em1时,请在其后打印行,并在下一行开始自动之前插入所需字符串。

这可能适用于GNU-sed:

sed '/^auto em1/!b;:a;$bb;n;/^auto/!ba;:b;idns-nameservers x.x.x.x' file
遇到自动em1时,请在其后打印行,并在下一行开始自动之前插入所需字符串

修改的测试数据:

$ cat foo
auto lo
iface lo inet loopback
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
测试它:

$ awk -f program.awk foo
auto lo
iface lo inet loopback
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
THE LINE
单行版本:

$ awk '/^auto/ && f { print "THE LINE"; f=0 } /^auto em1/ { f=1 } { print } END{ if(f==1) print "THE LINE" }' foo
修改的测试数据:

$ cat foo
auto lo
iface lo inet loopback
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
测试它:

$ awk -f program.awk foo
auto lo
iface lo inet loopback
auto eth1
iface eth1 inet static
address 192.168.3.155
netmask 255.255.255.0
dns-nameservers 8.8.8.8
auto em1
iface em1 inet static
address 192.168.2.98
netmask 255.255.255.0
gateway 192.168.2.1
THE LINE
单行版本:

$ awk '/^auto/ && f { print "THE LINE"; f=0 } /^auto em1/ { f=1 } { print } END{ if(f==1) print "THE LINE" }' foo

如果想要的自动块位于文件END{iff print…}的末尾,这将受益于END语句。不要紧,插入点在END模式之前。这可以更改,它可能是另一个文件中的另一行。@James Brown请查看新添加的示例。如果想要的自动块位于文件结尾{iff print…}的末尾,则使用END语句会有好处。不要紧,插入点在结束模式之前。这可以更改,这可能是另一个文件中的另一行。@James Brown请查看新添加的示例。非常感谢,最后一个示例是我想要的,我用其他设备替换了/em1/,它仍然可以正常工作。非常感谢,最后一个示例是我想要的,我用其他设备替换了/em1/,它仍然可以正常工作。非常感谢,这个例子适用于em1,但不适用于eth4,因为我相信这是我的例子中的最后一个设备,而且它的enrty不以auto结尾以EOF结尾?相反无论如何,谢谢你,一切都有帮助。非常感谢,这个例子适用于em1,但不适用于eth4,因为我相信这是我例子中的最后一个设备,它的enrty不会以EOF自动结束?相反无论如何,谢谢你,有什么帮助吗?@EdMorton我想说我做了,但根据我的指挥历史,我做错了。对此很抱歉,它似乎起作用了。@EdMorton我想说我做了,但根据我的命令历史,我做错了。很抱歉,这似乎有效。