shell正则表达式


函数,正则表达

 
本节内容
 
1. shell函数
2. shell正则表达式
 
shell函数
 
shell中允许将一组命令集合或语句形成一段可用代码,这些代码块称为shell函数。给这段代码起个名字称为函数名,后续可以直接调用该段代码。
 
格式
func() { #指定函数名
command #函数体
}
 
实例1:

#!/bin/bash
func() {
echo "This is a function."
}
func
# bash test.sh
This is a function.

Shell 函数很简单,函数名后跟双括号,再跟双大括号。通过函数名直接调用,不加小括号。
 
示例 2:函数返回值

#!/bin/bash
func() {
VAR=$((1+1))
return $VAR
echo "This is a function."
}
func
echo $?
# bash test.sh
2

return 在函数中定义状态返回值,返回并终止函数,但返回的只能是 0-255 的数字,类似于 exit。
 
示例 3:函数传参

#!/bin/bash
func() {
echo "Hello $1"
}
func world
# bash test.sh
Hello world

通过 Shell 位置参数给函数传参。
 
shell正则表达式
 
正则表达式在每种语言中都会有,功能就是匹配符合你预期要求的字符串。
Shell 正则表达式分为两种:
•  基础正则表达式
• 扩展正则表达式:扩展的表达式有+、?、| 和()
 
1. 正则表达式就是为了处理大量的文本|字符串而定义的一套规则和方法
2. 通过定义的这些特殊符号的辅助,系统管理员就可以快速过滤,替换或输出需要的字符串。Linux正则表达式一般以行为单位处理。
 
正则表达式和通配符有本质区别
 
 
1. 不需要思考的判断方法:在三剑客awk,sed,grep,egrep都是正则,其他都是通配符
2. 区别通配符和正则表达式最简单的方法:
(1)文件目录名===>通配符
              (2)文件内容(字符串,文本【文件】内容)===>正则表达式
 
下面是一些常用的正则表达式符号,我们先拿 grep 工具举例说明。
注意:在匹配模式中一定要加上引号
 
                  符号                                             描述                                                           实例                                
. 匹配任意单个字符(必须存在)  
例子:l..e
可以表示
love
like
leee
不可以表示的
labcde
le
lee
^    
匹配前面字符串开头 匹配以 abc 开头的行:
echo -e "abc\nxyz" |grep ^abc
$    
匹配前面字符串结尾 匹配以 xyz 结尾的行:
echo -e "abc\nxyz" |grep xyz$
*    
匹配前一个字符的零个或多个 a*  表示出现任意个a的情况
a*b 表示b前面有任意个a的情况(包括没有a的情况)
.*  表示任意长度的任意字符 例子:过滤出一行中a在前,b在后的行
条件:
包含 a 和 b
字母 a 必须在 b前面
 
# grep --color "a.*b" b.txt
+(扩展正则)    
表示其前面的字符出现最少一次的情况 匹配 abc 和 abcc:
echo -e "abc\nabcc\nadd" |grep -E 'ab+'
匹配单个数字:echo "113" |grep -o '[0-9]'
连续匹配多个数字:echo "113" |grep -E -o '[0-9]+'
?(扩展正则)    
表示其前面的字符出现最多一次的情况(可以0个) 匹配 ac 或 abc:
echo -e "ac\nabc\nadd" |grep -E 'a?c'
[]    
表示范围内的一个字符 例子:过滤出包含小写字母的行       grep [a-z] a.txt
例子:过滤出包含大写字母的行       grep [A-Z] a.txt
例子:过滤出包含数字的行           grep [0-9] a.txt
例子:过滤出包含数字和小写字母的行 grep [0-9a-z] a.txt
例子:过滤出包含字母asf的行        grep [asf] a.txt
[ .-.]    
匹配中括号中范围内的任意一个字符 匹配所有字母
echo -e "a\nb\nc" |grep '[a-z]'
[^]    
匹配[^字符]之外的任意一个字符 匹配 a 或 b:
echo -e "a\nb\nc" |grep '[^c-z]'
匹配末尾数字:echo "abc:cde;123" |grep -E
'[^;]+$'
^[^]    
匹配不是中括号内任意一个字符开头的行 匹配不是#开头的行:
grep '^[^#]' /etc/httpd/conf/httpd.conf
{n}或者{n,}    
{n}:表示严格匹配n个字符 echo "aadadccc" | egrep "a{2}"
{n,}匹配花括号前面字符至少 n个字符 echo "aadadccc" | egrep "a{1}"
{n,9m}    
匹配花、-括号前面字符至少 n个字符,最多 m 个字符 例子:
"ac\{2,5\}b" 匹配a和b之间有最少2个c最多5个c的行
"ac\{,5\}b" 匹配a和b之间有最多5个c的行
"ac\{2,\}b" 匹配a和b之间有最少2个c的行
\<    
 锚定单词首部(单词一般以空格或特殊字符做分隔) # echo "hi,root,iamroot" | grep "\<root"
hi,root,iamroot
# echo "hi,root,iamroot" | grep "root\>"
hi,root,iamroot
# echo "hi,root,iamroot" | grep "\<root\>"
hi,root,iamroot
 
\>  锚定单词尾部(单词一般以空格或特殊字符做分隔,)  
# echo "hi,root,iamroot" | grep "\<root"
hi,root,iamroot
# echo "hi,root,iamroot" | grep "root\>"
hi,root,iamroot
# echo "hi,root,iamroot" | grep "\<root\>"
hi,root,iamroot
()    
\1  调用前面的第一个分组  
例子:过滤出一行中有两个相同数字的行
# grep "\([0-9]\).*\1" inittab
 
例子:过滤出行首和行位字母相同的行
# grep "^\([a-z]\).*\1$" inittab
 
|(扩展正则)    
匹配竖杠两边的任意一个  
例子:过滤出cat 或者Cat
 
# grep "cat|Cat" a.txt
 
# grep "(C|c)at" a.txt
 
 
总结
 
正则表达式
 
一、字符匹配
点匹配任意单个字符
例子
[root@006 ~]# grep "r.t" 1
operator:x:11:0:operator:/root:/sbin/nologin
[root@006 ~]# grep "r..t" 1
root:x:0:0:root:/root:/bin/bash
operator:x:11:0:operator:/root:/sbin/nologin


^开头
例子
[root@006 ~]# grep "^root" 1
root:x:0:0:root:/root:/bin/bash

 $后别
例子
[root@006 ~]# grep "sync$" 1
sync:x:5:0:sync:/sbin:/bin/sync

空号
[root@006 ~]# grep -v "^$" 1

二、次数匹配
*后边为一定。前别0个或多个
[root@006 ~]# grep -n "n*c" 1
6:sync:x:5:0:sync:/sbin:/bin/sync

.* 匹配开头和结尾

[root@006 ~]# grep -n "r.*t" 1
1:root:x:0:0:root:/root:/bin/bash
10:operator:x:11:0:operator:/root:/sbin/nologin

[ ] 匹配是单个字符【a-zA-Z0-9】


\{m,n\}

[^]取反


 
开头取反


  \{\}


\>对符号有效
 

四、分组
  \1
 


扩展正则表达式
grep -E
egrep
 
一、字符匹配

+多个或一个

匹配
*
{m,n}
+ 表示其前面的字符出现最少一次的情况
?表示其前面的字符出现最多一次的情况
 

 

三、锚定
^
$
\<
\>
 
四、分组
  ()
  \1
  \2
 
五、或
|
 
一.、正则表达式中的{}以及()都需要加上\进行转义,而扩展正则表达式不需要
二 、|, ?,+是扩展正则独有的
三、 锚定单词首部和尾部在扩展正则以及正则中都需要加上\
 
                                  Posix字符                                                                                       描述                                                   
[:alnum:]  
等效a-zA-Z0-9
 
[:alpha:]  
等效a-zA-Z
[:lower:] 等效a-z
 
[:upper:] 等效A-Z
 
[:digit:]  
等效0-9
[:space:] 匹配任意空白字符,等效\t\n\r\f\v
 
[:graph:] 非空白字符
 
[:blank:] 空格与定位字符
 
[:cntrl:] 控00
 
[:print:]  
可显示的字符
[:punct:] 标点符号字符
 
[:xdigit:] 十六进制
 
 
注意:使用这些字符的时候需要在外面还要加一个[]括号
说一下[:space:]

[root@ken ~]# cat test #文本内容
#!/bin/bash
if [ 1 -eq 1 ];
then echo "yes"
else echo "no"
fi
AJDLAJDL
LAJLDJA
JDKAJkjskdjklaskj
lsdjal0dlkakm
[root@ken ~]# grep '[[:space:]]' test #过滤出包含空格的行,[:space:]括号外面还要再包含一个[]
if [ 1 -eq 1 ];
then echo "yes"
else echo "no"

[root@ken ~]# grep ' ' test #也可以使用一个空格来代替[:space:]
if [ 1 -eq 1 ];
then echo "yes"
else echo "no"

 
正则练习
 
使用文件 /etc/init.d/functions ,下面可能有些部分题目匹配不到符合的情况。
1. 过滤出包含大写字母的行
cat /etc/init.d/functions | grep "[A-Z]"

2. 匹配非数字字符
cat /etc/init.d/functions | grep "[^0-9]"
3. 过滤出一行中a在前,b在后的行
cat /etc/init.d/functions | grep "a.*b"
4. 匹配a和b之间有最少2个c最多5个c的行

5. 过滤出以# 为开头,且第二个字符是空格的行
grep "^# " /etc/init.d/functions
6.过滤出行首和行位字母相同的行
Grep "^\([a-z]).*\1$"
7.过滤出第一个字符是#,且第二个字符串是非空字符,而且结尾是数字的行

8.过滤出一行包含相同数字的行/etc/init.d/functions
 
 
 
 
答案:
1. 
[root@ken ~]# grep "[A-Z]" /etc/init.d/functions
 
2. 
[root@ken ~]# grep "[^0-9]" /etc/init.d/functions
 
3.
[root@ken ~]# grep "a.*b" /etc/init.d/functions
 
4.(匹配不到)
[root@ken ~]# grep "ac\{2,5\}b" /etc/init.d/functions
 
5.
[root@ken ~]# grep "^#[[:space:]]" /etc/init.d/functions
 
6.(匹配不到)
[root@ken ~]# grep "^\([a-z]\).*\1$" /etc/init.d/functions
 
7.(匹配不到)
[root@ken ~]# grep "^#[^[:space:]].*[0-9]$" /etc/init.d/functions
 
8.
[root@ken ~]# egrep ".*([0-9]).*\1" /etc/init.d/functions
 
补充:shell练习题
 
1. 每一秒钟输出/root下的文件至屏幕
2. 打印出包含某个关键词的文件(关键词执行脚本时接收)
3. 统计系统中以.sh结尾的文件总大小,输出结果以kb为单位
 
 
 
 
参考答案:
1. 
#!/bin/bash
for file in `ls /root`
do
echo $file
sleep 1
done
 
2.

#!/bin/bash
key=$1
for file in `find / -type f`
do
grep "$key" $file &>/dev/null
if [ $? -eq 0 ];then
echo $file
sleep 1
fi
done

 
3.

#!/bin/bash
sum=0
for size in `find /root -name "*.sh" -exec ls -l {} \; | cut -d " " -f 5`
do
let sum+=$size
done
echo "$((sum/1024))kb"


来自 <https://www.cnblogs.com/kenken2018/p/10229140.html>


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM