sed之G、H、g、h使用

sed如何处理数据?
shell

sed在正常状况下,将处理的行读入模式空间(pattern space),脚本中的“sed-command(sed命令)”就一条接着一条进行处理,知道脚本执行完毕。而后该行呗输出,模式(pattern space)被清空;接着,在重复执行刚才的动做,文件中的新的一行被读入,直到文件处理完毕。bash

 

什么是Pattern Space,什么是Hold Space?app

pattern space至关于车间sed把流内容在这里处理。spa

hold space至关于仓库,加工的半成品在这里临时储存。code

PS:你能够将pattern space当作是一个流水线,全部的动做都是在“流水线”上执行的;而hold space是一个“仓库”,“流水线”上的东东均可以放到这里。orm

为何要使用sed高级命令(G、H、g、h、n、N、x)?it

因为各类各样的缘由,好比用户但愿在某个条件下脚本中的某个命令被执行,或者但愿模式空间获得保留以便下一次的处理,都有可能使得sed在处理文件的时候不按照正常的流程来进行。这个时候,sed设置了一些高级命令来知足用户的要求。class

sed命令:awk

+ g:[address[,address]]g 将hold space中的内容拷贝到pattern space中,原来pattern space里的内容清除sed

+ G:[address[,address]]G 将hold space中的内容append到pattern space\n后

+ h:[address[,address]]h 将pattern space中的内容拷贝到hold space中,原来的hold space里的内容被清除

+ H:[address[,address]]H 将pattern space中的内容append到hold space\n后

+ d:[address[,address]]d 删除pattern中的全部行,并读入下一新行到pattern中

+ D:[address[,address]]D 删除multiline pattern中的第一行,不读入下一行

PS:不管是使用G、g仍是H、h,它们都是将hold space里面的内容“copy”到pattern space中或者将pattern space中的内容“copy”到hold space中。

附上英文的解释(注意其中的高亮单词):

The "h" command copies the pattern buffer into the hold buffer. The pattern buffer is unchanged.

Instead of exchanging the hold space with the pattern space, you can copy the hold space to the pattern space with the "g" command. This deletes the pattern space. If you want to append to the pattern space, use the "G" command. This adds a new line to the pattern space, and copies the hold space after the new line.

示例一:


#!/bin/bash
file=/tmp/volume_status_$$
ret=/tmp/volume_status_ret_$$

scnas volume status | grep -v "Scnas process" | grep -v "NFS Server" | grep -v "Self-heal" | sed s/'Status of volume: '/'卷名:'/g | grep -v "\-\-\-" | sed s/'Brick '//g >$file

while read line;do
	echo $line | grep "卷名" 1>/dev/null
	if [ $? -ne 0 ];then
		brick=$(echo $line | awk -F ' ' '{printf $1}')
		statu=$(echo $line | awk -F ' ' '{printf $3}')
		if [ X$statu == 'XY' ];then
			statu='在线'
			printf "$brick\t\t$statu\n" >>$ret
		elif [ X$statu == 'XN' ];then
			statu='离线'
			printf "<font color='red'>$brick\t\t$statu</font>\n" >>$ret
		fi
	else
		echo " " >>$ret
		printf "$line\n" >>$ret
		echo "--------------------------" >>$ret
	fi
done <$file
cat $ret
rm -f $file $ret

示例二:用sed模拟出tac的功能(倒序输出)。

文件内容

cat mm
1
2
3

解决方法:

sed ‘1!G;h;$!d’mm

ps:1!G第1行不 执行“G”命令,从第2行开始执行。

       $!d,最后一行不删除(保留最后1行)

图解分析过程

P:Pattern Space

H:Hold Space

蓝色:Hold Space中的数据

绿色:Pattern Space中的数据

参考:

《sed and awk 第二版》

相关文章
相关标签/搜索