文本处理三剑客(grep/sed/awk)

grep和egrep过滤器

grep

  1. 第一种形式: grep [option] [pattern] [file1,file..]
  2. 第二种形式: command| grep [option] [pattern]

选项option

常用选项

选项 含义
-V 不显示匹配行信息
-i 搜索时忽略大小写
-n 显示行号
-r 递归搜索
-E 支持扩展正则表达式
-F 不按正则表达式匹配,按照字符串字面意思匹配

不常用选项

选项 含义
-c 只显示匹配行总数
-w 匹配整词
-x 匹配整行
-l 只显示文件名,不显示内容
-s 不显示错误信息

grep和egrep:

  • grep默认不支持扩展正则表达式,只支持基础正则表达式
  • 使用grep-E可以支持扩展正则表达式
  • 使用egreep可以支持扩展正则表达式,与grep -E等价

sed 流编辑器

sed(Stream Editor),流编辑器。对标准输出或文件逐行进行处理
格式

  • 第一种形式: stdout | sed [option] “pattern command”
  • 第二种形式: sed [option] “pattern command” file

sed选项

选项 含义
-n 只打印模式匹配行
-e 直接在命令行进行sed编辑,默认选项
-f 编辑动作保存在文件中,指定文件执行
-r 支持扩展正则表达式
-i 直接修改文件内容
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
[root@master datas]# cat sed.txt 
I love shell
I love SHELL
axcz
caxa


[root@master datas]# sed -n '/Shell/p' sed.txt
I love shell

# 多个comand时必须加-e
[root@master datas]# sed -n '/shell/p' sed.txt
I love shell

[root@master datas]# sed -n -e '/shell/p' -e '/SHELL/p' sed.txt
I love shell
I love SHELL

# -f
# edit.sed中有 /SHELL/p
[root@master datas]# sed -n '/SHELL/p' sed.txt
I love SHELL

[root@master datas]# sed -n -f edit.sed sed.txt
I love SHELL

# -r
[root@master datas]# sed -n -r '/SHELL|shell/p' sed.txt
I love shell
I love SHELL

# -i
[root@master datas]# sed -n 's/love/like/g;p' sed.txt
I like shell
I like SHELL
axcz
caxa
[root@master datas]# cat sed.txt
I love shell
I love SHELL
axcz
caxa
# 加-i直接将原文件修改
[root@master datas]# sed -n -i 's/love/like/g;p' sed.txt
[root@master datas]# cat sed.txt
I like shell
I like SHELL
axcz
caxa

sed Pattern用法

匹配模式 含义
10command 匹配到第10行
10,20command 匹配从第10行开始,到第20行结束
10, +5command 匹配从第10行开始,到第16行结束
/pattern1/command 匹配到pattern1的行
/pattern1/,/pattern2/command 匹配到pattern1的行开始,到匹配到pattern2的行结束
10,/pattern1/command 匹配从第10行开始,到匹配到pettern1的行结束
/pattern1/,10command 匹配到pattern1的行开始,到第10行匹配结束
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
1、LineNumber   ---直接指定行号
sed -n "17p" file 打印file文件的第17行

2、StartLine , EndLine --指定起始行号和结束行号
sed -n "10,20p" file 打印file文件的10到20行

3、Star tLine, +N 指定起始行号,然后后面N行
sed -n "10,+5p" file 打印file文件中从第10行开始,往后面加5行的内容

4、/pattern1/ ----------------正则表达式匹配的行
sed -n "/^root/p" file 打印file文件中以root开头的行

5、/pattern1/,/pattern2/ ---从匹配到pattern1的行,到匹配到pattern2

...

案例–查找配置文件中配置项段名与段的个数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
#!/bin/bash


FILE_NAME=/opt/datas/openssl.cnf

function get_all_segment
{
segments="`sed -n '/\[ .* \]/p' $FILE_NAME | sed -n 's/\[ \(.*\) \]/\1/g;p'`"
echo $segments
}

function count_segment_num
{
echo "`sed -n '/\[ '$1' \]/,/\[/p' $FILE_NAME | sed -n -e '/=/p' | grep -v ^\# -c`"
}

number=1
for segment in `get_all_segment`
do
echo "$number: $segment `count_segment_num $segment`"
number=`expr $number + 1`
done

案例


sed 中的编辑命令详解

  1. 查询

    1. p 打印
  2. 增加

    1. a 行后追加
    2. i 行前追加
    3. r 外部文件读入,行后追加
    4. w 匹配行写入外部文件

    追加内容

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    1、a
    (1)、passwd文件第10行后面追加"Add Line Behind"
    sed -i '10a Add line behind' passwd
    (2)、passwd文件第10行到第20行,每一-行后面都追加"Test Line Behind"
    sed -i '10,20a Test Line Behind' passwd
    (3)、passwd文 件匹配到/bin/bash的行后面追加"Insert Line For /bin/bash Behind"
    sed -i '/\/bin\/bash/a Insert Line For /bin/bash Behind' passwd
    2、i
    (1)、passwd文件匹配到以tss开头的行,在匹配航前面追加"AddLineBefore"
    sed -i '/^tss/i Add a line before it' passwd
    (2)、passwd文件每一行前面都追加"Insert Line Before Every Line"
    sed -i 'i Insert a line before every line' passwd
    3、r
    (1)、将/opt/datas/anotation文 件的内容追加到passwd文件的第20行后面
    sed -i '20r /opt/datas/anotation' passwd
    (2)、将/etc/inittab文件内容追加到passwd文件匹配/sbin/nologin行的后面
    sed -i '/\/sbin\/nologin/r /opt/datas/anotation' passwd
    (3)、将/opt/datas/anotation文件内容追加到passwd文件中特定行后面,匹配以ftp开头的行,到第18行的所有行
    sed -i '/ftp/,18r /opt/datas/anotation' passwd
    4、w
    (1)、将passwd文件匹配到/bin/bash的行追加到/opt/datas/sed.txt文件中
    sed -i '/\/bin\/bash/w /opt/datas/sed.txt' passwd
    (2)、 将passwd文件从第10行开始,到匹配到tss开头的所有行内容追加到/opt/datas/sed-1.txt
    sed -i '10,/^tss/w /opt/datas/sed-1.txt' passwd
  3. 删除

    1. d 删除
      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      19
      20
      21
      22
      23
      1、删除/etc/passwd中的第15行
      sed -i '15d' /etc/passwd
      2、删除/etc/passwd中的第8行到第14行的所有内容
      sed -i '8,14d' /etc/passwd
      3、删除/etc/passwd中的不能登录的用户(筛选条件: /sbin/nologin)
      sed -i '/\/sbin\/nologin/d' /etc/passwd
      4、删除/etc/passwd中以mai1开头的行,到以yarn开头的行的所有内容
      sed -i '/^mai1/,/^yarn/d' /etc/passwd
      5、删除/etc/passwd中第一个不能登录的用户,到第13行的所有内容(少用)
      sed -i '/\/sbin\/nologin/,13d' /etc/passwd
      6、删除/etc/passwd中 第5行到以ftp开头的所有行的内容
      sed -i '5,/^ftp/d' /etc/passwd
      7、删除/etc/passwd中以yarn开头的行到最后行的所有内容
      sed -i '/^yarn/,$d' /etc/passwd
      8、删除/etc/passwd中不能登录的所有用户
      sed -i '/\/sbin\/nologin/d' /etc/passwd

      典型需求
      1、删除配置文件中的所有注释行和空行
      sed -i '/^#/d;/^$/d' openssl.cnf
      sed -i '/[:blank:]*#/d' openssl.cnf # 删除空格行的注释,但对openssl.cnf无效
      2、在配置文件中所有不以#开头的行前面添加*符号,注意:以#开头的行不添加
      sed -i 's/^[^#]/\*&/g' openssl.cnf
  4. 修改

    1. s/old/new 将行内第一个old替换为new
    2. s/old/new/g 将行内全部的old替换为new
    3. s/old/new/2g 将行内前2个old开始替换所有为new
    4. s/old/new/ig 将行内olg全部替换为new ,忽略大小写
      修改命令对照表

    | 编辑命令 | 含义 |
    | —————————— | ———————————————————— | |
    | 1s/old/new/ | 替换第1行内容old为new |
    | 1,10s/old/new/ | 替换1行到10行的内容old为new |
    | 1, +5s/old/newl | 替换1行到6行的内容old为new |
    | /pattern1/s/old/new/ | 替换匹配到pattern1的行内容old为new |
    | /pattrn1/,/pattern2/s/old/new/ | 替换匹配到pattern1的行直到匹配到pattern2的所有行内容old为new |
    | /pattern1/, 10s/old/new/ | 替换匹配到pattern1的行到10行的所有行内容old为new |
    | 10,/pattern1/s/old/new/ | 替换第10行直到匹配到pattern1的所有行内容old为new |

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    1、修改/etc/passwd中第1行中第1个root为ROOT
    sed -i '1s/root/ROOT/' /etc/passwd
    2、修改/etc/passwd中第5行到第10行中所有的/sbin/nologin为/bin/bash
    sed -i '1,10s/\/sbin\/nologin/\/bin\/bash/' /etc/passwd
    3、修改/etc/passwd中匹配到/sbin/nologin的行, 将匹配到行中的login改为大写的LOGIN
    sed -i '/\/sbin\/nologin/s/login/LOGIN/g' /etc/passwd
    4、修改/etc/passwd中从匹配到以root开头的行,到匹配到行中包含mail的所有行。修改内为将这些所有匹配的行中的bin改为HADOOP
    sed -i '/^root/,/mail/s/bin/HADOOP/g' passwd
    5、修改/etc/passwd中从匹配到以root开头的行,到第15行中的所有行,修改内容为将这些行中的nologin修改为SAPRK
    sed -i '/^root/,15s/nologin/SPARK/g' passwd
    6、修改/etc/passwd中从第15行开始,到匹配到以tss开头的所有行,修改内容为将这些行中的bin换为BIN
    sed -i '15,/^tss/s/bin/BIN/g' passwd
  5. 其他

    1. = 查看行号不显示内容

什么是反向引用?


什么是反向引用?

使用&或\1可以表示前面匹配到的,使用\1需要加括号,其中&查找部分原封不动的取代

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
[root@master datas]# cat test 
hadoop
hadAAp
hadBBp
hadCCp
hadDDp

sed -i 's/had..p/&s/g' test

[root@master datas]# cat test
hadoops
hadAAps
hadBBps
hadCCps
hadDDps

[root@master datas]# sed -i 's/\(had..p\)/\1S/g' test
[root@master datas]# cat test
hadoopSs
hadAApSs
hadBBpSs
hadCCpSs
hadDDpSs
# 部分取代进行修改,用括号括住引用部分
[root@master datas]# sed -i 's/\(had\)...../\1oop/g' test
[root@master datas]# cat test
hadoop
hadoop
hadoop
hadoop
hadoop

有变量时使用双引号或将变量用单引号引起来


awk报告生成器

Comments

Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×