sed正则的贪婪
shell中sed 利用正则表达式匹配字符串时,默认使用贪婪模式,且只有贪婪模式,没有非贪婪模式。
unterminated `s’ command问题:正则表达式$与自定义命令边界符
# 使用#作为自定义的边界
sed -i "s#^basedir=$#basedir=$basedir#g" $directory/$dirname/support-files/mysql.server
# 使用@作为自定义的边界
sed -i "s@^basedir=$@basedir=$basedir@g" $directory/$dirname/support-files/mysql.server
# 使用%作为自定义的边界
sed -i "s%^basedir=$%basedir=$basedir%g" $directory/$dirname/support-files/mysql.server
# 使用|作为自定义的边界
sed -i "s|^basedir=$|basedir=$basedir|g" $directory/$dirname/support-files/mysql.server
上面四行代码都是用以替换某文件下某字段的代码,但是在实际运行使用#和@符号作为自定义边界的代码却会出现unterminated `s' command
的问题。
为什么会导致这样的问题呢?
首先,在终端中执行set -x
(参见Shell set),之后分别执行上述命令,会发现,使用#和@符号作为自定义边界的代码$#和$@的部分都不见了,这是由于shell自身的内置变量导致的问题。因此,在使用$限定正则匹配结束字串的时候,自定义的边界符(姑且这么称之),形成的字串,不能与shell自身的内置变量一致。这是由于sed会默认先解析表达式中的变量,再执行sed命令导致的。
为什么要使用自定义边界符?
待替换的变量中如果出现了默认边界符/
,则需要使用自定义的边界符。否则就只能提前在变量中执行转义操作。需要注意的是,如果变量中或者查找、替换字串中出现了自定义的边界符,同样需要对边界符进行转义操作。