grep命令:Linux系统中grep命令是一种强大的文本搜索工具,它能使用正则表达式搜索文本,并把匹 配的行打印出来
语法:
grep [-abcEFGhHilLnqrsvVwxy][-A<显示列数>][-B<显示列数>][-C<显示列数>][-d<进行动作>][-e<范本样式>][-f<范本文件>][--help][范本样式][文件或目录...]
参数:
-
options:
-E : 使用扩展正则表达式进行匹配, grep -E 或取代 egrep 命令。
-F : 使用固定字符串进行匹配, grep -F 或取代传统的fgrep命令。
-e : 通常第一个非选项的参数认为是要匹配的模式,也可以同时提供多个模式,只要将其放入单引号,并用换行字符分隔他们。
模式以减号开头时,为防止混淆其为选项,-e选项说明其后的参数为模式,即使他以减号开头。
-f : 从pat-file文件读取模式作为匹配。
-i : 模式匹配时忽略大小写差异。
-l : 列出匹配模式的文件名称,而不是打印匹配的行。
-q : 静默的,如果匹配成功,不将匹配的行输出到标准输出;否则即是不成功。
-s : 不显示错误信息,通常与-q并用。
-v : 显示不匹配模式的行。
说明:可以同时查找多个文件中的内容,当指定多个文件时,每个显示出的文件行前会有文件名加一个冒号标识其来自哪个文件。
可以使用多个-e 或 -f 选项,建立要查找的模式列表。
实例:
1、在当前目录中,查找后缀有"test"字样的文件中包含"test"字符串的文件,并打印出该字符串的行。此时,可以使用如下命令:
grep test *file
结果如下所示:
$ grep test test* #查找后缀有“test”的文件包含“test”字符串的文件
testfile1:This a Linux testfile! #列出testfile1 文件中包含test字符的行
testfile_2:This is a linux testfile! #列出testfile_2 文件中包含test字符的行
testfile_2:Linux test #列出testfile_2 文件中包含test字符的行
2、以递归的方式查找符合条件的文件。例如,查找指定目录/etc/acpi 及其子目录(如果存在子目录的话)下所有文件中包含字符串"update"的文件,并打印出该字符串所在行的内容,使用的命令为:
grep -r update /etc/acpi
输出结果如下:
$ grep-r update /etc/acpi #以递归的方式查找“etc/acpi”
#下包含“update”的文件
/etc/acpi/ac.d/85-anacron.sh:# (Things like the slocate updatedb cause a lot of IO.)
Rather than
/etc/acpi/resume.d/85-anacron.sh:# (Things like the slocate updatedb cause a lot of
IO.) Rather than
/etc/acpi/events/thinkpad-cmos:action=/usr/sbin/thinkpad-keys--update
3、反向查找。前面各个例子是查找并打印出符合条件的行,通过"-v"参数可以打印出不符合条件行的内容。
查找文件名中包含test 的文件中不包含test 的行,此时,使用的命令为:
grep -v test*
结果如下所示:
$ grep-v test* #查找文件名中包含test 的文件中不包含test 的行
testfile1:helLinux!
testfile1:Linis a free Unix-type operating system.
testfile1:Lin
testfile_1:HELLO LINUX!
testfile_1:LINUX IS A FREE UNIX-TYPE OPTERATING SYSTEM.
testfile_1:THIS IS A LINUX TESTFILE!
testfile_2:HELLO LINUX!
testfile_2:Linux is a free unix-type opterating system.
4.
当前目录及其子目录下搜索'math'行的文件,但是不显示匹配的行,只显示匹配的文件
$ grep -l -r 'math' *
s.txt
5.
正则表达式
-E : 使用扩展正则表达式进行匹配, grep -E 或取代 egrep 命令。
支持正则语法,单引号里面写正则。
1.正则表达式的组成
(1).一般字符:没有特殊意义的字符
(2).特殊字符(meta字符):元字符,有在正则表达式中有特殊意义
2.如下讲下正则表达式中的常见meta字符
(1).POSIX BRE与ERE中都有的meta字符:
\ : 通常用于打开或关闭后续字符的特殊含义,如\(...\)与\{...\}
. : 匹配任何单个字符(除NUL)
* : 匹配其前的任何数目或没有的单个字符,例: . 表示任一字符, 则 .* 匹配任一字符的任意长度
^ : 匹配紧接着的正则表达式,BRE中仅在正则表达式的开头有特殊的含义,ERE中在任何位置都有特殊含义
$ : 匹配前面的正则表达式,在字符串或者行结尾处。BRE中仅在正则表达式的结尾处有特殊的含义,ERE中在任何位置都有特殊含义
[] : 匹配方括号内的任一字符,其中可用连字符(-)指的连续字符的范围;^符号苦出现在方括号的第一个位置,则表示匹配不在列表中的任一字符,
(2).POSIX BRE中才有的字符:
\{n,m\} : 区间表达式,匹配在它前面的单个字符重现的次数区别。\{n\}指重现n次;\{n,m\}指重现n至m次;
\( \) : 保留空间,可以将最多9个独立的子模式存储在单个模式中。如\(ab\).*\1 : 指匹配ab组合的两次重现,中间可存在任意数目的字符。
\n : 重复在\(与\)方括号内第n个子模式至此点的模式。
(3).POSIX ERE中才有的字符:
{n,m} : 与BRE的\{n,m\}功能相同
+ : 匹配前面正则表达式的一个或多个扩展
? : 匹配前面正则表达式的零个或一个扩展
| : 匹配|符号前或后的正则表达式
( ) : 匹配方括号括起来的正则表达式群
(4). 方括号([])表达式
4.1.字符集 [: :]
标识字符集,有如下几种:
[::alnum] : 数字字符 | [:digit:] : 数字字符 | [:punct:] : 标点符号字符 |
[:alpha:] : 字母字符 | [:graph:] : 非空格字符 | [:space:] : 空格字符 |
[:blank:] : 空格与定位字符 | [:lower:] : 小写字母字符 | [:upper:] : 大写字母字符 |
[:cntrl:] : 控制字符 | [:print:] : 可显示的字符 | [:xdigit:] : 16进制数字 |
4.2.排序符号
指将多个字符视为一个符号,如[.ch.]即将ch视为一个符号
4.3.等价字符
认为多个字符相等,如[=e=]在法文的locale里,可匹配于多种与e相似的字符,此处不再列出。
说明:这三种构造除其自身的方括号之外,还必须使用额外的方括号括起来。
例 : [[:alpha:]!] : 匹配任一英文字母或感叹号。
[[.ch.] : 匹配ch排序元素,而不匹配单独的字母c或h.
3.简单正规表达式匹配案例
china : 匹配此行中任意位置有china字符的行
^china : 匹配此以china开关的行
china$ : 匹配以china结尾的行
^china$ : 匹配仅有china五个字符的行
[Cc]hina : 匹配含有China或china的行
Ch.na : 匹配包含Ch两字母并且其后紧跟一个任意字符之后又有na两个字符的行
Ch.*na : 匹配一行中含Ch字符,并且其后跟0个或者多个字符,再继续跟na两字符
awk简介
awk是一个强大的文本分析工具,相对于grep的查找,sed的编辑,awk在其对数据分析并生成报告时,显得尤为强大。简单来说awk就是把文件(或其他方式的输入流, 如重定向输入)逐行的读入(看作一个记录集), 把每一行看作一条记录,以空格(或\t,或用户自己指定的分隔符)为默认分隔符将每行切片(类似字段),切开的部分再进行各种分析处理。
awk有3个不同版本: awk、nawk和gawk,未作特别说明,一般指gawk,gawk 是 AWK 的 GNU 版本。
Awk基本语法:
awk 'pattern1 {command1;command 2…; command 3} pattern2 { command …}'
pattern表示用来过滤记录的模式,可是是正则表达式,关系运算表达式,也可以什么也没有(表示选中所有记录)。
每个pattern选中的行记录会被花括号括起来的命令command操作一遍, command之间用;
分割。 花括号里面可以什么也没有, 则默认为print输出整行记录。 Comamnd可以是输出, 可以是算术运算,逻辑运算,循环控制等等。
示例
s.txt
zhangsan 1977 male computer 83
lisi 1989 male math 99
wanglijiang 1990 female chinese 78
xuliang 1977 male economic 89
xuxin 1986 female english 99
wangxuebing 1978 male math 89
lichang 1989 male math 99
wanglijiang 1990 female chinese 78
zhangsansan 1977 male computer 83
langxuebing 1978 male math 89
lisibao 1989 male math 99
xiaobao 1990 female chinese 78
一行中的5个字段分辨表示姓名, 出生年, 性别,科目,分数, 是一个很传统很典型的报表文件。
现在演示awk是如何查找的:
1)直接输出1990年出生的同学:
$ awk '/1990/' s.txt
wanglijiang 1990 female chinese 78
wanglijiang 1990 female chinese 78
xiaobao 1990 female chinese 78
或者:
$ awk '/1990/{print $0}' s.txt
$0
表示匹配所有列。
2)对chinese的课程的行输出"语文":
$ awk '/chinese/{print "语文"}' s.txt
语文
语文
语文
3)记录的头部和结尾加上一段说明:
$ awk 'BEGIN{print "Result of the quiz:\n"}{print $0}END{print "------"}' s.txt
Result of the quiz:
zhangsan 1977 male computer 83
lisi 1989 male math 99
wanglijiang 1990 female chinese 78
xuliang 1977 male economic 89
xuxin 1986 female english 99
wangxuebing 1978 male math 89
lichang 1989 male math 99
wanglijiang 1990 female chinese 78
zhangsansan 1977 male computer 83
langxuebing 1978 male math 89
lisibao 1989 male math 99
xiaobao 1990 female chinese 78
------
4)查找女生的成绩且只输出姓名、学科、成绩:
$ awk '$3=="female"{print $1,$4,$5}' s.txt
wanglijiang chinese 78
xuxin english 99
wanglijiang chinese 78
xiaobao chinese 78
$1
表示第1列,$n
类推。这里条件是表达式,而不是正则。print里,
表示空格分隔符。
5)找出1990年出生的学生姓名,并要求匹配正则:
$ awk '$2~/1990/{print $1}' s.txt
wanglijiang
wanglijiang
xiaobao
这里~
表示匹配正则表达式。!~
表示不匹配正则表达式。
6) 找出大于1985年出生的学生姓名,年龄,使用表达式:
$ awk '$2>"1985"{print $1,$2}' s.txt
lisi 1989
wanglijiang 1990
xuxin 1986
lichang 1989
wanglijiang 1990
lisibao 1989
xiaobao 1990
awk内置变量
awk有许多内置变量用来设置环境信息,这些变量可以被改变,下面给出了最常用的一些变量。
ARGC 命令行参数个数
ARGV 命令行参数排列
ENVIRON 支持队列中系统环境变量的使用
FILENAME awk浏览的文件名
FNR 浏览文件的记录数
FS 设置输入域分隔符,等价于命令行 -F选项
NF 浏览记录的域的个数
NR 已读的记录数
OFS 输出域分隔符
ORS 输出记录分隔符
RS 控制记录分隔符
$0 指整条记录
$1, $2, … $n 当前记录的字段
示例:
6)第四个字段科目为chinese的记录编号, 学生姓名, 科目:
$ awk '$4=="chinese"{print NR, $1, $4, $5}' s.txt
3 wanglijiang chinese 78
8 wanglijiang chinese 78
12 xiaobao chinese 78
7)统计数学成绩大于90的个数:
$ awk 'BEGIN{goodMath=0;}($4=="math" && $5>90){goodMath++}END{print goodMath}' s.txt
3
8)显示最近登录的5个帐号
$ last -n 5 | awk '{print $1}'
root
root
root
dmtsai
root
9)更换行分隔符为;
:
$ cat /etc/passwd |awk -F ':' '{print $1}'
root
daemon
bin
sys
-F
指定域分隔符为:
。
10)批量操作
# 关闭所有正在运行容器
docker ps | awk '{print $1}' | xargs docker stop
# 删除所有容器应用
docker ps -a | awk '{print $1}' | xargs docker rm
sed
和grep、awk不同,sed更侧重对搜索文本的处理,如修改、删除、替换等等。
sed主要用来自动编辑一个或多个文件;简化对文件的反复操作;编写转换程序等。
语法
sed [-hnV][-e<script>][-f<script文件>][文本文件]
参数说明:
-e<script>或--expression=<script> 以选项中指定的script来处理输入的文本文件。
-f<script文件>或--file=<script文件> 以选项中指定的script文件来处理输入的文本文件。
-h或--help 显示帮助。
-n或--quiet或--silent 仅显示script处理后的结果。
-i 直接编辑文件而不是显示在屏幕上
-V或--version 显示版本信息。
动作说明:
a :新增, a 的后面可以接字串,而这些字串会在新的一行出现(目前的下一行)~
c :取代, c 的后面可以接字串,这些字串可以取代 n1,n2 之间的行!
d :删除,因为是删除啊,所以 d 后面通常不接任何咚咚;
i :插入, i 的后面可以接字串,而这些字串会在新的一行出现(目前的上一行);
p :列印,亦即将某个选择的数据印出。通常 p 会与参数 sed -n 一起运行~
s :取代,可以直接进行取代的工作哩!通常这个 s 的动作可以搭配正规表示法!例如 1,20s/old/new/g 就是啦!
sed命令必须跟一个动作。
新建文件t.txt:
zhangsan 1977 male computer 83
lisi 1989 male math 99
wanglijiang 1990 female chinese 78
1)新增一行:第3行后新增:
$ sed -e '3a newline'
zhangsan 1977 male computer 83
lisi 1989 male math 99
wanglijiang 1990 female chinese 78
newline
2)插入一行:第3行前插入:
$ sed -e '3i newline'
zhangsan 1977 male computer 83
lisi 1989 male math 99
newline
wanglijiang 1990 female chinese 78
3)删除一行:删除第3行:
$ sed -e '3d'
zhangsan 1977 male computer 83
lisi 1989 male math 99
4)替换一行:
$ sed -e '3c newline'
zhangsan 1977 male computer 83
lisi 1989 male math 99
newline
5)行内部分内容的替换:
格式:
sed 's/要被取代的字串/新的字串/g'
示例:
$ sed '3s/1990/2000/g' t.log
zhangsan 1977 male computer 83
lisi 1989 male math 99
wanglijiang 2000 female chinese 78
6)多行操作:
$ sed '2,3d' t.log #删除2,3行
$ sed '2,$d' t.log #从第2行开始删除到末尾
$ sed '2,3a test' t.log #分别在第2行,第3行增加字符"test"
注意:
1、上述的操作均只在输出缓冲里操作,文件并没有变化;需要直接修改文件,前面加-i
参数;
2、-e
参数可以没有。
Xargs
之所以能用到这个命令,关键是由于很多命令不支持|
管道来传递参数,而日常工作中有有这个必要,所以就有了xargs
命令,例如:
find /sbin -perm +700 |ls -l #这个命令是错误的
find /sbin -perm +700 |xargs ls -l #这样才是正确的
http://www.runoob.com/linux/linux-comm-grep.html