Linux文本三剑客

grep

文本过滤工具.

作用: 文本搜索工具,根据用户指定的行进行匹配检查,打印匹配到的行.

模式: 由正则表达式字符及文本字符所编写的过滤条件.

grep的使用

语法:  grep [OPTIONS] PATTERN FILE....  

选项

选项 说明
--color=auto 对匹配到的文本着色显示
-v 显示不被pattern匹配到的行
-i 忽略字符大小写
-n 显示匹配的行号
-c 统计匹配的行数
-o 仅显示匹配到的字符串
-q 静默模式,不输出任何信息
-A # after,后@行
-B # before,前#行
-C # context, 前后各#行
-e 实现多个选项间的逻辑or关系
-w 匹配整个单词
-E 使用扩展正则表达式,相当于egrep
-F 相当于fgrep,不支持正则表达式

正则表达式

链接:http://www.yanshicheng.com/archives/redhat/linux/linux%e4%b9%8b%e6%ad%a3%e5%88%99%e8%a1%a8%e8%be%be%e5%bc%8f.html https://www.cnblogs.com/yanshicheng/p/12323782.html

 sed

行编辑器,sed是一种流编辑器他一次处理一行内容.处理时,把当前处理的行存储在临时缓冲区中,称为"模式空间",接着用sed命令处理缓存区中的内容,处理完成后把缓存区中的内容送往屏幕,然后读取下一行,执行下一个循环,

主要用于自动编辑一个或者多个文件,简化对文件的操作,编写转换程序等.

sed的使用

语法:  sed [OPTIONS].... 'script' inputfile....  

常用选项

选项 说明
-n 不输出模式空间内容到屏幕,即为不自动打印
-e 多点编辑
-f /PATH/SCRIPT_FILE 从指定文件中读取编辑脚本
-r 支持使用正则表达式
-i.bak 直接修改源文件,先备份为.bak

地址定界

1) 不给地址 对全文进行处理
2) 单地址
    #: 指定的行.$为最后一行
    /pattern/: 被此处模式所能匹配的行
3) 地址范围
    #,#:    指定从#行开始到#行结束
    #,+#    指定从#行开始在此基础相加几行
    /pat1/,/pat2/   指定从模式1到模式2
    #,/pat1/        指定几行到模式1
4) ~ 步进
    1~2    奇数行
    2~2    偶数行编辑编辑

编辑命令

d: 删除模式空间匹配的行,并立即启用下一轮循环 
p: 打印行钱模式空间的内容,追加到默认输出 
a [\]text: 在指定行后面追加文件,支持使用\n实现多行追加  例:awk '/^root/a\root' password 
i [\]text: 在行前面插入文本 
c [\]text: 替换行为单行或者多行文本 
w /path/somefile: 保存模式匹配的行值指定的文件 
r /path/somefile: 读取指定文件的文本至模式空间中,匹配到的行后. 
=: 为模式空间中的行打印行号 !: 模式空间中匹配行取反处理 
s///: 查找替换,支持使用其他分隔符,s@@@,s### 
    替换标记: 
        g: 行内全局替换 
        p: 显示替换成功的行 
        w /path/to/somefile: 将替换陈宫的行保存至文件中

进阶命令

P:    打印模式空间开头至\n内容,并追加到默认输出之前.
h:    把模式空间中的内容覆盖至保持空间中.
H:    把模式空间中的内容追加至保持空间中.
g:    把保持空间中的内容覆盖至模式空间中.
G:    把保持空间中的内容追加至模式空间中.
x:    把模式空间中的内容与保持空间中的内容进行互换.
n:    读取匹配到的行的下一行覆盖至模式空间中.
N:    读取匹配到的行的下一行追加至模式空间中.
d:    删除模式空间中的行.
D:    如果模式空间包含换行符,则删除知道第一个换行符的模式空间中的文本,并不会读取新的输入行,二使用和成的模式空间重新启动循环,如果模式空间不包含换行符,则会像发出d命令那样正常的新循环.

awk

AWK是一种优良的文本处理工具。它不仅是 Linux 中也是任何环境中现有的功能最强大的数据处理引擎之一。这种编程及数据操作语言(其名称得自于它的创始人 Alfred Aho 、Peter Weinberger 和 Brian Kernighan 姓氏的首个字母)的最大功能取决于一个人所拥有的知识。AWK 提供了极其强大的功能:可以进行样式装入、流控制、数学运算符、进程控制语句甚至于内置的变量和函数。它具备了一个完整的语言所应具有的几乎所有精美特性。实际上 AWK 的确拥有自己的语言:AWK 程序设计语言, 三位创建者已将它正式定义为“样式扫描和处理语言”。它允许您创建简短的程序,这些程序读取输入文件、为数据排序、处理数据、对输入执行计算以及生成报表,还有无数其他的功能。

awk使用

awk用法:  awk OPTIONS '/模式/{print $0}' aa.txt 

awk选项

选项 说明
-F 指明输入时用到的字段分隔符
-v var=value 自定义变量

awk操作符

操作符 说明
~ 包含 例子  root~$2
!~ 不包含
&& and
||
== 等于
!= 不等于
< <= 大于, 大于等于
<  <= 小于, 小于等于
--,++ 自加自减

BEGIN&END

语法:  awk 'BEGIN{}/模式/{操作}END{}' file 

BEGIN: 处理之前要执行的某些操作如:打印一些字符,设置变量值.

END: 处理之后要执行的某些操作如:打印一些字符,做最终运算.

例子:

awk 'BEGIN{FS="[:]";aa=1}{print $aa}' password 

awk 'BEGIN{FS="[:]"}{aa+=$3}END{print "所 有的UID的和是:",aa}' password

  

常见的内置变量

选项 说明
FS 输入字段分隔符,默认为空白符
OFS 输出字段分隔符,默认为空白符
NF 字段数量
RS 输入记录分隔符,指定输入时的分隔符
ORS 输出记录分隔符,输出时用指定符号代替换行符.
FILENAME 当前文件名
NR 记录号 NR==FNR 处理第一个文件 NR!=FNR 处理第二个文件
FNR 个文件分别计数,记录号.
ARGC 命令行参数的个数
ARGV 数组,保存的是命令行所给定的参数.

if-else语句

语法:

if(判断1){语句1}else{语句2}
if(判断1)(语句1)else if(判断2)(语句2)else{语句3}
awk '/模式/{if(判断语句){语句1}}'

三目表达式

语法: (条件?"语句1":语句2)  

例:

awk -F"[:]" '{if($3==0){print $1"是root"}else if($3==2){print $1"是系统用户"}else{print $1"啥也不是"}}' password 

for循环

语法: for (变量初始值;变量范围;变量增长幅度){命令}  

例:

for(i=1;i<=10;i++){}
awk -F: '{for (i=1;i<=NF;i++){if($i==root){print $0}}}' password
awk -F: '{for (i=1;i<=NF;i++){print $i}}' password

While循环

语法:  while (判断){语句} 

例:

awk -F: '{print "---------";i=1;while(i<=NF){print $i;i++}}' password 

Awk控制语句

break     只能在循环语句中使用,如果遇到break的话,那么跳出循环.
continue  只能在循环语句中使用,如果遇到continue的话那么结束本次循环进行下次循环.
next      可以在循环语句中和判断语句中使用,next在循环语句中功能和break类似,在判断语句中结束对本行处理二直接进入下一行处理.

awk数组

  • 数组的下标可以是数组或者字母
  • 使用数组可以不是连续数字
  • 使用字母必须使用双引号

数组的定义:

a[1]="aa"
a[2]="bb"
a[3]="cc"

数组的引用:  数组名[下标] 

数组的删除:  delete 数组名[下标] 

判断在不在数组中:  if("xx" in aa){print "ok"} 

awk内置函数

sub     字符替换,只能替换第一个
        使用方法: sub("old","new",目标)
        示例: awk '{sub("root","ROOT");print $0}' password 

gsub    字符替换,全局替换
        使用方法: gsub("old","new",目标)
        示例: awk '{gsub("root","ROOT");print $0}' password 

length  判断单词字符长度
        示例: awk -F: '{print $1,length($1)}' password

substr 用来截取一段数据
       使用方法: substr("原始数字",数字,长度)
       示例: awk -F: '{print substr($1,2,2)}' password

match   某种格式的字符在指定字符的第几个位置出现
        使用方法:match("原始字符",/格式/)
	    RSTART 可以获取match所得到的那个值
	    RLENGTH	表示的是match中满足格式的那个字符的长度
	示例: awk -F: '{xx=match($0,/\/sbin.*/);print xx}' password 

  
split    把指定的字符串,安好某种分隔符,分割成数组
         使用方法: split("原始字符",数组名)    如果没有指定分隔符,使用的是FS
                  split("原始字符",数组名,分隔符)
         示例: echo "" |  awk '{split ("2014-12-12",xx,"-");print xx[1]}'


getline  读取本文件的下一行
        示例: awk -F: '{if($3==1){getline;print $0}}' password
 
getline  变量 把本文的下一行赋值给变量
         示例: awk -F: '{if($3==1){getline gg;print gg}}' password
         : getline < file 服务file这个文件的一行赋值给 getline

本章练习题

1、显示/proc/meminfo文件中以不区分大小的s开头的行;

2. 使用egrep 在/matching/gg.txt 文件中找到ab123 类词语


3. 使用egrep 在/matching/gg.txt 提取192.168.0.1


4. 使用sed 在/matching/gg.txt 提取192.168.0.1


5. 使用sed 在/matching/passwd 文件删除第一行,全部root 修改为ROOT,并备份源文件
    
7. 使用awk 找到/matching/access.log 访问IP前10的ip,并使用其他方式完成
  

8. /matching/下面 vv.txt,nn.txt 按照数字合并例如:001 北京 朝阳区 法拉利 使用awk 完成
   

9. 计算/matching/ling文件$3的和 不能使用-F指定分隔符,分隔符为:。
  
10. 输出/matching/ling文件 $3如果大于1000输出此用户为系统用户,并带用户名字和UID,大于1000为普通用户,等于则打印用户名
    

答案:

 

1、显示/proc/meminfo文件中以不区分大小的s开头的行;
    grep -i ^s /proc/meminfo

2. 使用egrep 在/matching/gg.txt 文件中找到ab123 类词语
egrep -o "\<[[:alpha:]]{2}[[:digit:]]{3}\>" gg.txt 

3. 使用egrep 在/matching/gg.txt 提取192.168.0.1
    egrep  -o "^i.*1" gg.txt | egrep  -o "[[:digit:]]{3}.[[:digit:]]{3}.[[:digit:]].[[:digit:]]"


4. 使用sed 在/matching/gg.txt 提取192.168.0.1
    sed -rn "3s#.*:(.*) H.*#\1#gp" gg.txt

5. 使用sed 在/matching/passwd 文件删除第一行,全部root 修改为ROOT,并备份源文件
    sed -i.bak "1d;s#root#ROOT#g" passwd
7. 使用awk 找到/matching/access.log 访问IP前10的ip,并使用其他方式完成
   awk '{a[$1]++}END{for(i in a){print i,a[i]}}' access.log | sort -k 2n -n | tail -10
   cut -d" " -f1 access.log | sort -rn |  uniq -cd | sort -rn | head -10

8. /matching/下面 vv.txt,nn.txt 按照数字合并例如:001 北京 朝阳区 法拉利 使用awk 完成
    awk 'NR==FNR{a[$1]=$0}NR!=FNR{print a[$1],$2}' vv.txt nn.txt

9. 计算/matching/ling文件$3的和 不能使用-F指定分隔符,分隔符为:。
    awk  'BEGIN{FS="[:]"}{a+=$3}END{print a}' ling

10. 输出/matching/ling文件 $3如果大于1000输出此用户为系统用户,并带用户名字和UID,大于1000为普通用户,等于则打印用户名
    awk -F: '{if($3<1000){print "系统用户为:",$1,"UUID为:",$3}else if($3>1000){print "普通用户为:",$1,"UUID为:",$3}else{print "用户为:",$1}}' ling 

  

 

posted @ 2020-02-17 22:12  闫世成  阅读(588)  评论(0编辑  收藏  举报