Sed 替换 bash 中的非注释行
Sed replace non-commented lines in bash
我觉得我快要解决这个问题了,但还不能完全解决。
我有一个脚本可以搜索以查看是否在 /etc/rc.local
中调用了实用程序。如果不是,我想在文件末尾 exit 0
之前的行中添加一行调用它。到目前为止,我有这个:
sudo sed -i 's/.*exit 0.*/'$UTILITY_PATH'\n&/' /etc/rc.local
这种方法有效,但也匹配带有 "exit 0" 的行作为注释 - 进一步出现 /etc/rc.local
以提醒用户确保脚本应以此行结尾。
所以,为了清楚起见,以下内容应该匹配:
exit 0
exit 0
exit 0
等等。以下不应匹配:
#exit 0
# exit 0
# blah blah "exit 0" blah blah
# exit 0
任何人都可以指出正确的方向吗?
我猜你想要这个:
sed -r -i 's/^\s*exit\s{1,}[0-9]/foo\n&/' /etc/rc.local
它匹配 exit [0-9]
- 前面和中间可能有 space。
顺便说一句,您还可以执行两者,如果找到模式则进行搜索,并且可以使用 awk
:
一步插入
awk '/foo/{m=1}/^\s*exit\s+[[:digit:]]/&&!m{print "foo"}1' /etc/rc.local
较新版本的 GNU awk
也支持就地编辑:
awk -i inplace '/foo/{m=1}/^\s*exit\s+[[:digit:]]/&&!m{print "foo"}1' /etc/rc.local
这是关于 regular expressions 的问题,对吧?你想要的是 exit 0
的匹配,除非它前面有 #。这个呢?
sudo sed -i 's/^[^#]*exit 0.*/'$UTILITY_PATH'\n&/' /etc/rc.local
你在车道中间有'#'吗?
因为如果 '#' 是第一个可打印字符,那么您就处于非常容易的位置:
再使用一个正则表达式(这里非常简单)来确定 sed 操作的范围,就像这样:
sed '/^\W*#/ ! s/something_u_want/whatever_u_want/ ' /etc/rc.local
/^\W*#/
表示 sed 将仅适用于对这个正则表达式进行数学运算的行,否则什么都不做
感叹号只是否定,所以条件是相反的——现在 sed 将只适用于这些不从 '#'
开始的行
if # isnt first then...嗯...也许:
sed '/^[^#]*exit 0/ s/something_u_want/whatever_u_want/ ' /etc/rc.local
我觉得我快要解决这个问题了,但还不能完全解决。
我有一个脚本可以搜索以查看是否在 /etc/rc.local
中调用了实用程序。如果不是,我想在文件末尾 exit 0
之前的行中添加一行调用它。到目前为止,我有这个:
sudo sed -i 's/.*exit 0.*/'$UTILITY_PATH'\n&/' /etc/rc.local
这种方法有效,但也匹配带有 "exit 0" 的行作为注释 - 进一步出现 /etc/rc.local
以提醒用户确保脚本应以此行结尾。
所以,为了清楚起见,以下内容应该匹配:
exit 0
exit 0
exit 0
等等。以下不应匹配:
#exit 0
# exit 0
# blah blah "exit 0" blah blah
# exit 0
任何人都可以指出正确的方向吗?
我猜你想要这个:
sed -r -i 's/^\s*exit\s{1,}[0-9]/foo\n&/' /etc/rc.local
它匹配 exit [0-9]
- 前面和中间可能有 space。
顺便说一句,您还可以执行两者,如果找到模式则进行搜索,并且可以使用 awk
:
awk '/foo/{m=1}/^\s*exit\s+[[:digit:]]/&&!m{print "foo"}1' /etc/rc.local
较新版本的 GNU awk
也支持就地编辑:
awk -i inplace '/foo/{m=1}/^\s*exit\s+[[:digit:]]/&&!m{print "foo"}1' /etc/rc.local
这是关于 regular expressions 的问题,对吧?你想要的是 exit 0
的匹配,除非它前面有 #。这个呢?
sudo sed -i 's/^[^#]*exit 0.*/'$UTILITY_PATH'\n&/' /etc/rc.local
你在车道中间有'#'吗? 因为如果 '#' 是第一个可打印字符,那么您就处于非常容易的位置: 再使用一个正则表达式(这里非常简单)来确定 sed 操作的范围,就像这样:
sed '/^\W*#/ ! s/something_u_want/whatever_u_want/ ' /etc/rc.local
/^\W*#/
表示 sed 将仅适用于对这个正则表达式进行数学运算的行,否则什么都不做
感叹号只是否定,所以条件是相反的——现在 sed 将只适用于这些不从 '#'
if # isnt first then...嗯...也许:
sed '/^[^#]*exit 0/ s/something_u_want/whatever_u_want/ ' /etc/rc.local