返回首页 两个月精通 Shell 脚本

shell 学习第七天----基础正则表达式 (BRE)

查找文本

用到的关键字 grep,最简单的用法就是使用固定字符串。

比如使用 who 命令查找当前多少人登陆系统

  • who |grep syx,就可以查看名字叫 syx 的用户登录于何处。
  • grep 的语法:
  • grep [options pattern-spec [files...]

用途: 显示匹配一个或者多个模式的文本行。时常为作为管道的第一步,以便对匹配的数据进一步处理。

主要选项

  • -i: 模式匹配时忽略大小写
  • -V: 显示不匹配的行
  • -l: 列出匹配模式的文件名称,而不是打印匹配的行
  • -n: 列出检索目标所在的行号
  • -c: 统计匹配的行总数,不显示航信息

行为模式

读取命令行上致命的每个文件,发现匹配查找迷失的行时,将它显示出来,当指名多个文件时,grep 会在每一行前面加上文件名与一个冒号。

  • grep: 最常用,可以检索目标 (一个活多个单词或正则表达式)。
  • fgrep: 不能使用正则表达式,可以检索多个目标,等同于 grep -f
  • egrep: 支持丰富的正则表达式,而且支持多目标检索,等同于 grep -e。

一般情况下没有使用 fgrep 的,我们也不建议使用。

说起文本检索就不得不提到正则表达式,正则表达式十一中表示方法,可以查找匹配特定准则的文本。例如,查找以”a” 字母开头的文本。茨表示法可以写一个表达式,选定或匹配多个数据字符串。

从根本上来看,正则表达式是由两个基本组成部分所建立:一般字符与特殊字符。一般字符指的是任何没有特殊意义的字符。在某些情况下,特殊特殊字符也可以视为一般字符。特殊字符称为元字符(metacharacter)。

  • BRE: 基本正则表达式(Basic Regular Expression)
  • ERE: 扩展的正则表达式(Extended Regular Expression)

先来看一些简单的匹配返利

  • tolstoy: 匹配一行上任意位置的 7 个字母:tolstoy
  • ^tolstoy: 7 个字母 tolstoy,出现在一行的开头
  • tolstoy$: 出现在一行的结尾
  • ^tolstoy$: 正好包含这 7 个字母的一行,没有其他的任何字符。
  • [tT]olstoy: 在一行的任意位居中,含有 Tolstoy 或者 tolstoy
  • tol.toy: 在一行的任意位居中,含有 tol 这三个字母,加上一个特殊字符,在接着 toy 这三个字母
  • tol.*toy: 在一行的任意位居中,含有 tol 这三个字母,加上任意的 0 或者多个字符,再继续 toy 这三个字母 (例如:toltoy,tolstoy,tolWHOtoy 都是满足要求的)。

shell 中的通配符: *: 代表 0 个或者多个任意字符 ?: 代表一定有一个的任意字符 []: 代表一定有一个在括号内的字符 (非任意字符)。例如 [abcd] 代表一定有一个字符,可能是 abcd 这四个选项的任意一个。 [-]: 若邮件韩在括号内时,代表在编码顺序内的所有自负。例如:[0-9] 代表 0 到 9 之间的所有数字,因为数字的语系编码是连续的。 [^]: 若括号内的第一个字符为指数字符 (^),那表示反向选择,例如:[^abc] 代表一定有一个字符,只要是非 abc 的其他字符就可以。

shell 中的特殊字符

  • #: 注释字符
  • \: 将特殊字符或者通配符还原成一般字符
  • |: 管道符,分割两个管线命令的界定
  • ;: 连续命令下达分隔符
  • ~: 用户的家目录
  • $: 放在变量前面,正确使用变量
  • &: 工作控制,将命令编程背景下工作
  • !: 非 (!) 的意思,逻辑运算符
  • ,>>: 输出重定向,分别是覆盖和追加

  • <,<<: 输入重定向
  • ‘’: 单引号,不具有变量置换的功能
  • “”: 双引号,具有变量置换的功能
  • (): 在中间的为子 shell 的起始与结束
  • {]: 在中间为命令块的组合

shell 中正则表达式的控制字符

  • ^: 匹配行首位置
  • $: 匹配行尾位置
  • .: 匹配任意祖父
  • : 对 之前的匹配整体或字符匹配任意次 (包括 0 次)
  • \?: 对 \? 之前的匹配整体或字符匹配 0 次或 1 次
  • {n}: 对 \ { 之前的匹配整体或字符匹配 n 次
  • {m,}: 对 \ { 之前的匹配整体或字符匹配至少 m 次
  • {m,n}: 对 \ { 之前的匹配整体或字符匹配 m 到 n 次
  • [abcdef]: 对单字符而言匹配 [] 中的字符
  • [a-z]; 对单字符而言,匹配任意一个小写字母

基本正则表达式

匹配单个字符

  1. 匹配一般字符: 一般字符是指无特殊含义的字符,包括所有文本和数字字符,绝大多数的空白字符以及标点符号字符,因此,正则 a,匹配 a。
  2. 如果相匹配 ,因为 是特殊字符,所以需要用 \ 转义,正则 *,匹配 *。
  3. (点号) 字符意即” 任意字符”,例如 a.c 匹配于 abc,aac。
  4. 使用方括号表达式。例如 x[abcdefg]z,可以匹配 xaz,xbz,等,方括号里如果存在 (^),表示取反的意思,就是说不匹配列表里的任意字符。

[0123456789] 表示所数字,但是这样写太麻烦,我们可以用 [0-9] 来表示,[abcdefg] 同样可以用 [a-g]

单个表达式匹配多字符

最简单的办法就是把它们一一列出来: 正则 abc 匹配于 abc。虽然 (.)meta 字符与方括号表达式都提供了依次匹配一个字符的很好方式,单正则真正强大而有力地功能是修饰符 meta 字符的使用上。最常用的修饰符是 (),表示匹配 0 个或多个前面的单个字符。因此 abc 表示” 匹配一个 a,0 个或多个 b 字符以及 a 空 c”。这个正则匹配的有 ac,abc,abbcabbbbc。匹配 0 或多个,不表示匹配其他的某一个。例如正则 ab*c,文本 aQc 是不匹配的。但是 ac 是匹配的。

  • (*) 修饰符虽然好用,但是他没有限制,如要只要指定次数,使用一个复杂的方括号表达式虽然也能指定次数,但是太过麻烦。我们就引入了区间表达式。所谓的区间表达式有三种变化
  • {n} 前置正则表达式所得结果重现 n 次
  • {n,} 前置正则表达式所得结果至少出现 n 次
  • {n,m} 出现 n 到 m 次

例如我们想要表达” 重现 5 个 a” =>a{5},” 重现 10 到 42 个 q”=>q{10,42};

文本匹配锚点

两个 meta 字符是脱节符号 (^),与货币字符 (&),他们叫做锚点,因为其用途在限制正则表达式匹配时,针对要被匹配字符的开始或者结尾处进行匹配,假定有一串字符串:abcABCdefDEF

正则表达式锚点的范例

模式 是否匹配 理由
ABC 居中的 4,5,6 字符匹配
^ABC 起始处不是 ABC
def$ 结尾处不是 def
[[:upper:]]{3} 居中的大写 ABC 匹配
[[:upper:]]{3}$ 结尾的大写 DEF 匹配
^[[:alpha:]]{3} 起始处的 abc 匹配

^ 和 $ 当然能同时使用,这种情况将括起来的正则表达式匹配整个字符串 (或行)。有时 ^$ 这样简易的正则很好用,可以用来匹配空的字符串或行列。例如加上 grep -v 选项用来显示所有不匹配模式的行们使用上面的做法,便能过滤掉文件里的空号。 ^$ 尽在起始与结尾具有特殊用处。例如 ab^cd 里的 ^ 表示的就是自身 (^)。

  • BRE 运算符哟普先机,由高到低
  • [..] [==] [::] 用于字符拍的方括号符号
  • \metacharacter 转移的 meta 字符
  • [] 方括号表达式
  • {} 子表达式
    • {} 前置单个字符重现的正则表达式
  • 无符号 连续
  • ^$ 锚点