专题 (四) sed
一、替换
1、简单替换
sed 's/正则表达式/替换后的内容/g'
“g”:表示全局替换
这个替换之后仅会写入缓存中,并不会持久化保存下来
2、从文件匹配,替换后写入文件
sed -i 's/正则表达式/替换后的内容/g' file
这个表示从 file 文件中进行匹配和替换
3、复杂匹配替换
sed -i 's#\(target1 \).*\( target2\)#[g]\1替换为新内容\2#' file
当加上 g 表示 将文件中所有 target1与target2之间的内容替换为 “替换为新的内容”
\(....\)是声明一个要保留的内容, 这里的 \1 对应的就是 就是 第一个 \(....\),\2 对应的就是 就是 第二个 \(....\)
sed -i '/匹配字符串1/s#\(target1 \).*\( target2\)#[g]\1替换为新内容\2#' file
针对含有 “匹配字符串1” 的行 将 target1与target2之间的内容替换为 “替换为新的内容” (当然前提时,一行的内容中含有 “匹配字符串1” 及 “target1” "target2")
4、替换的内容为一个 shell 脚本中的变量
sed 's/匹配内容/'"${replace}"'/'
要使用 '"${var}"' 才行,否则不生效
5、指定行更改
sed -i '2c 替换内容' file
将文件中第二行内容 整个替换为 “替换内容” (整行替换)
sed -i '3s/匹配内容/替换内容/数字' file
表示将第三行中和 "匹配内容" 匹配到的地方 替换成 “替换内容” ,若数字给值,则表明仅替换匹配上的第几个,没有给值,默认替换匹配上第 “数字”个, 也可以 设置 g ,表示全部替换。
示例:
1、替换字符串中含有的ip
待补充
2、替换 json 中某个属性的值
文件(test.txt)内容:
{ "service":{ "id":"service-112", "name":"serviceA", "address":"127.0.0.1", "port":8080, "tags":["contextPath=/"], "checks": [ { "http":"127.0.0.1:8080/", "interval":"10s" } ] } }
sed -i 's#\("interval":"\).*\("\)#\120s\2#' test.txt 表示把 "interval":" 和 " 之间的内容替换成 20s ,上述示例就是将 10s 替换成 20s.
执行以上的内容,最后会发现 修改成功;不过以上有一个弊端 ,会进行每行匹配,只要匹配到就进行替换
3、双重匹配替换
文件内容如下:
java -jar xxx.jar &
nohup java -jar xxx.jar &
nohup sh xxx.sh &
java nohup -jar xxx.jar &
sed -i '/nohup/s#\(-jar \).*\(.jar\)#\1yyy\2#' /opt/test.txt
修改后的文件内容如下:
java -jar xxx.jar & nohup java -jar yyy.jar & nohup sh xxx.sh & java nohup -jar yyy.jar &
4、目标值为 shell 变量
文件内容如下:
java -jar xxx.jar & nohup java -jar xxx.jar & nohup sh xxx.sh & java nohup -jar xxx.jar &
replace='kkk'
sed -i '/nohup/s#\(-jar \).*\(.jar\)#\1'"${replace}"'\2#' /opt/test.txt
修改后的文件内容如下:
java -jar xxx.jar & nohup java -jar kkk.jar & nohup sh xxx.sh & java nohup -jar kkk.jar &
5、 更改指定行内容
文件内容如下:
test1111
test2222
sed -i '2c testkkkk' /opt/test.txt
更改后的文件内容如下:
testkkk
test2222
6、指定行进行匹配,匹配上的话进行替换
文件内容如下:
test1111
test2222
test1111test2222
sed -i '3s/test/temp/2' /opt/test.txt
更改后的文件内容如下:
testkkk
test2222
test1111temp2222
7、将字符串的最后一个字符进行替换
字符串内容如下:
"{\"hello\":\"test\",\"hello2:\":\"test2\"}"
a="{\"hello\":\"test\",\"hello2:\":\"test2\"}"
echo $a |sed 's/\(.*\)"\(.*\)/\1\2/' //表示将最后一个字符串 " 换成空格
字符串更改后的内容如下:
"{\"hello\":\"test\",\"hello2:\":\"test2\"}
8、将所有空格换掉
echo $a | sed s/[[:space:]]//g
将变量 a 中值字符串中的空格都替换掉
9、替换路径中的 / 杠,并要求可以匹配上 / ,替换成 \/
test_home="/opt/os/sky/test" test_home_tmp=`echo $test_home |sed 's/\//\\\\\//g'` #目标将 exist_in_ld_count=`sed -n '/^'"${test_home_tmp}"'/p' /etc/ld.so.conf |wc -l`
10、将指定内容行的指定字符串之后的内容全部换掉
properties 文件内容为:
port=7019
现需要将7019换成8017
port=8017
sed -i 's#\(port=\).*\(.*\)#\1'"$port"'\2#' rsyncd.conf
二、匹配查询
(1) 仅展示匹配的内容
sed -n '/正则表达式/p' file
若没有 -n ,则会展示所有内容 + 匹配的内容,匹配的内容在文件内容展示完之后显示
示例:
1. 获取含有指定网卡的内容
ifconfig | sed '$!N;/'${local_ip}'/{P;d};D' | awk -F ':' '{print$1}' |sed s/[[:space:]]//g
PS: 注意这里有个${local_ip},local_ip 是shell 变量,这里要通过该变量直接取其值,在 ${变量名} 上要加上 '' 变为 ‘${变量名} ’,否则无法正确取得该值。
2、返回符合条件的上一行
文件内容:
sky up
water
sky down
命令:
sed -n '/water/{g;p};h' /opt/test.txt
更新后的文件内容:
sky up
http://www.bathome.net/thread-53545-1-1.html
3、返回符合条件的下一行
文件内容:
sky up
water
sky down
命令:
sed -n '/water/{n;p};' /opt/test.txt
查询结果:
sky down
4、匹配数字(行仅有数字)
文件内容如下:
test2222
test1111temp2222
delete me
when match me then delete me
12345
命令:
sed -n '/^[0-9]\+$/p' file
输出内容:
12345
5、返回 匹配 上的 两个关键字之间的行
原内容:

命令:
./rabbitmqctl cluster_status |sed -n '/Disk Nodes/,/Running Nodes/p'
输出内容:

(2)properties 中 value 值获取
properties文件中的格式:
k=value
value=`awk -F= -v k=key '{ if ( $1 == k ) print $2; }' "$COMDIR/conf/config.properties" | sed 's/\r//' #其中 key 需要换成真实的值
通过以上命令可以获得 key 的 值 value.
三、删除
(1) 指定行进行删除
sed -i '数字d' file
表示将 file 中指定 “数字”行给删除掉,并更新到文件中。如果 没有 “-i” ,则表示操作的内容不写入到 file文件中。
(2) 删除匹配的行
sed -i '/匹配内容/d' file
表示删除含有 “匹配内容的” 行,并生效到文件中
或者使用正则表达式
sed -i '/正则表达式/d' file
示例:
1、删除行首空格
sed ‘s/^[ \t]*//g'
说明:
第一个/的左边是s表示替换,即将空格替换为空。
第一个/的右边是表示后面的以xx开头。
中括号表示“或”,空格或tab中的任意一种。这是正则表达式的规范。
中括号右边是*,表示一个或多个。
第二个和第三个\中间没有东西,表示空
g表示替换原来buffer(缓冲区)中的,sed在处理字符串的时候并不对源文件进行直接处理,先创建一个buffer,但是加g表示对原buffer进行替换
整体的意思是:用空字符去替换一个或多个用空格或tab开头的本体字符串
2、删除行末空格
sed ‘s/[ \t]*$//g'
和上面稍微有些不同是前面删除了^符,在后面加上了美元符,这表示以xx结尾的字符串为对象。
但是要注意在KSH中,Tab并不是\t而是直接打入一个Tab就可以了。
3、删除所有的空格
sed s/[[:space:]]//g
4、删除指定行的内容
文件内容如下:
delete me
命令:
sed -i '1d' /opt/test.txt
更新后的文件内容:
文件为空的
5、删除匹配内容的行
原有文件内容:
when match me then delete me
命令:
sed -i '/match/d' /opt/test.txt
更新后的文件内容:
文件为空的
6、删除指定行的上一行
sed -i -e :a -e '$!N;s/.*\n\(.*ServerName abc.com\)/\1/;ta' -e 'P;D' $file
7、删除指定字符串之间的内容
sed -i '/ServerName abc.com/,/\/VirtualHost/d' $file
8、删除空行
sed /^$/d filename 删除空行
四、增加
1、在匹配行之后插入数据
sed -i '/正则表达式/a追加内容' file
表示在文件中若有和正则表达式匹配的行,则在下一行插入“追加内容”
2、在匹配行之前插入数据
sed -i '/正则表达式/i追加内容' file
表示在文件中若有和正则表达式匹配的行,则在上一行插入“追加内容”
3、在指定行之后插入数据
sed -i '行号 a追加内容' file
表示在指定行"行号"后一行中插入“追加内容”,更新的部分写入到file
4、在指定行之前插入数据
sed -i '行号 i追加内容' file
表示在指定行"行号"前一行中插入“追加内容”,更新的部分写入到file
示例:
1、在匹配的行之后插入数据
文件内容:
12345
命令:
sed -i '/123/a3456' /opt/test.txt
更新后的文件内容
12345 3456
2、在匹配的行上一行插入数据
文件内容:
12345
命令:
sed -i '/123/i3456' /opt/test.txt
更新后的文件内容:
3456 12345
3、在指定行的后一行中插入数据
文件内容:
12345
命令:
sed -i '1 a1011' /opt/test.txt
更新后的文件内容:
12345 1011
4、在指定行的前一行中插入数据
文件内容:
12345
命令:
sed -i '1 i1011' /opt/test.txt
更新后的文件内容:
1011 12345
五、其他
1、-e (在一行中执行多条命令)
sed -e '命令1;命令2'
示例:
1、在一行中进行多个目标替换
sed -e 's/wang/w/g;s/xu/x/g' user.txt //表示将wang 替换成 w,将 xu 替换成 x
参考资料:
https://www.jb51.net/article/57972.htm
https://blog.csdn.net/wdz306ling/article/details/80087889 (推荐,这里面的内容还是蛮全的)
https://www.cnblogs.com/noobkey/p/4951941.html
http://www.04007.cn/article/676.html (这个里面的可以具体再看看,还有些没有看懂)
https://blog.csdn.net/weixin_38629422/article/details/91881624

浙公网安备 33010602011771号