awk与sed、grep一样都是为了加工数据流而做成的文本加工过滤器命令。awk会事先把输入的数据根据字段单位进行分割。在没有指定分割单位的情况下,以输入数据中的空格或Tab为分隔符。与sed相比,它以更接近编程语言的文法进行处理,还包括了通过正则表达式进行的字符串操作、简单的数学函数功能等。

sed的基本形式

sed 启动选项 '地址 命令/查找字符串/替换字符串/标志' 输入.txt > 输出.txt

启动选项

​ -e '单行脚本'; -f 脚本文件; -g 整个文章作为对象(global)

​ -i 将结果覆盖到源输入文件中,可以指定后缀名生成备份文件,如-i.bak

地址

举例 含义
(空,未指定) 所有行
2 第2行
11,$ 11~最后一行
4,10! 4~10行以外的行
/^[0-9]/ 所有以数字开头的行
2,/END$/ 从第2行开始到以END结尾的行

命令 可以使用;分割组合使用多个命令,按顺序执行。

s字符串替换;y字符替换;d删除;

p直接输出;w文件输出;n数据输入

双直引号与单直引号为了防止其中的字符作为shell的特殊字符处理。

sed命令操作

s命令替换字符串

cat /etc/passwd | sed "s!/bin/bash$!/bin/zsh!g"

表示将行末以/bin/bash结尾的行中的/bin/bash替换为/bin/zsh其中感叹号!为分隔符,也可以用/、\、#、甚至任意的英文字母,只要不与要替换的字符串发生混淆即可。标志g表示将整个文档作为替换范围,而不是仅替换第一次出现的位置。

sed -e 's!//!#!' hello.c #将//替换为#

sed -e 's/var/+&+/g' a.txt #将var替换为+var+

sed -e 's/.*/result: &/gw output.txt' a.txt

&表示对前边待替换字符串中正则表达式匹配的字符串的引用。

w 指定输出文件名,将替换后的结果写到文件。

y命令替换字符

sed -e 'y/abc/xyz' a.txt #同时进行a->x, b->y, c->z的替换

d命令删除行

sed -e '1,5d' a.txt #删除前5行后输出剩余内容

sed -e 'd' a.txt #删除全文,输出为空,输入文件并不改变

p命令输出

sed -n -e '2,$p' a.txt

sed -n -e '/^aaa/,/eee$/p' a.txt #以aaa开头的行到以eee结尾的行

脚本文件中命令的组合

对于一个地址可以执行{多个命令}

2,6{
命令1
命令2
....
}

脚本文件结构-标签、分支、循环

: 标签
命令1,2,3...
/模式/b 标签
命令x

示例-删除所有换行符合并字符串

:loop		#循环执行的开始位置
N #字符串合并
$!b loop #不是最后一行时跳转
s/\n//g #删除换行符

awk

基本用法

命令基本用法:awk [-F域分隔符] '{pattern + action}' {filenames}

默认的域分隔符是空格,可以指定'\t','\n'等分隔符。其中 pattern 表示 awk 在数据中查找的内容,而 action 是在找到匹配内容时所执行的一系列命令。

通常,awk 是以文件的一行为处理单位的。awk 每接收文件的一行,然后执行相应的命令,来处理文本。

待处理的文件可以是多个,后面有处理多个文件的例子。

支持awk '/正则表达式/' testfile 筛选匹配的行,支持sub,match,split等正则表达式函数。

正则表达式匹配查找(match使用)

$ awk 'BEGIN{info="this is a test2010test!";print match(info,/[0-9]+/)?"ok":"no found";}'

ok

awk内置变量

变量 解释
$n 当前记录的第n个字段,n为1表示第一个字段
$0 执行过程中当前行的文本内容
ARGC 命令行参数的数目
ARGV 包含命令行参数的数组
ARGIND 命令行中当前参数的位置(从0开始算)
CONVFMT 数字转换格式(默认值为%.6g)
ENVIRON 环境变量关联数组
ERRNO 最后一个系统错误的描述
FIELDWIDTHS 字段宽度列表(用空格键分隔)
FILENAME 当前输入文件的名字
FS 字段分隔符(默认是任何空格)
FNR 当前行在正在处理的文件中的行号
NR 在执行过程中对应于当前的行号(已处理的所有文件的记录数)
NF 表示字段数,在执行过程中对应于当前的字段数
OFMT 数字的输出格式(默认值是%.6g)
OFS 输出字段分隔符(默认值是一个空格)
ORS 输出记录分隔符(默认值是一个换行符)
RS 记录分隔符(默认是一个换行符)
RSTART 由match函数所匹配的字符串的第一个位置
RLENGTH 由match函数所匹配的字符串的长度
SUBSEP 数组下标分隔符(默认值是34)
IGNORECASE 如果为真,则进行忽略大小写的匹配

print $NF打印一行中最后一个字段; $(NF-1)代表倒数第二个字段。

awk内置函数

awk提供了一些内置函数,方便对原始数据的处理。如函数toupper($1)用于将字符串$1转为大写。

  • length():返回字符串长度。
  • substr():返回子字符串。
  • sin():正弦。
  • cos():余弦。
  • sqrt():平方根。
  • rand():随机数。

示例1-脚本

可以编写awk脚本,然后传给awk进行解释执行:awk -f awk-script-file input-file(s)

awk统计各个登录shell的用户数:

$ awk '
BEGIN{ FS=":" } #修改字段分隔符为:
{ shells[$NF]++;} #NF保存的是输入行的字段数,$NF可以访问最后一个字段的值
END{
for(sh_i in shells)
print sh_i ": " shells[sh_i];#输出类似/bin/bash: 3
}' /etc/passwd

示例2-日志解析

  1. 输出特定行

    sed -e '100,200p' 文件名

  2. 统计行数

    awk '{count++} END {print count}' 文件名

  3. 统计目录下文件的总大小

    ls -l | awk '{size+=$5} END {print size}'

  4. 在控制台中高亮显示一些信息

    sed -e 's/\(Failed password\)/\x1b[1;36;44m\1\x1b[0m/' /var/log/secure

    其中\x1bESC这一字符的16进制表示,1;36;44表示文字风格;文字颜色;背景色,用[x;y;zm表示这个组合的绑定,\x1b[0m表示文字修饰结束。中间的\1引用前面匹配的\(内容\)

    可选高亮设置

    文字风格
    0 重置风格
    1 粗体
    4 下划线
    5 点线
    7 颜色反转
    8 隐藏
    值(文字颜色/背景色) 文字颜色/背景色
    30/40
    31/41
    32/42 绿
    33/43
    34/44
    35/45 红紫
    36/46 蓝绿
    37/47
  5. 显示出现频率较高的top 10个字符串,如访问源IP

    awk '{print $1}' access_log | sort | uniq -c | sort -nr | head -10

    注意uniq的去重统计是按照相邻行计算的,只走一遍,所以需要在uniq -c之前先进行sort按字符顺序进行排序。

  6. 条件筛选-根据URL请求计算疑似非法访问的日志数量

    awk '$9 !~ /200|304/{print $9,$7}' access_log |sort| uniq -c | sort -nr

    $9 !~ /模式/表示筛选掉$9中满足该模式的字符串

示例3-同时处理两个文件

awk 'pattern' file1 file2

在awk里,NR和FNR的含义相近,唯一的区别就是作用范围,NR是所有读取的行信息计数,而FNR是正在读取文件的行信息技术,FNR在文件切换时会从0重新开始计数,所以在awk语句中:

  • NR==FNR在判断是不是在读file1;
  • NR>FNR则判断是不是在读file2.

awk求两个文件的交集(有相同字段的行)

awk -F'\t' 'NR==FNR{cat[$1]=1}NR>FNR{if($1 in cat){print $0}else{}}' file1 file2

代码的含义是首先处理file1时NR==FNR,执行cat[$1]=1,表示创建一个cat词典,当处理file2时,判断file2中的行是否在cat字典中,并进行print $0(一整行)

awk按照奇数行和偶数行进行处理

使用NR或FNR进行判断,awk '{if (NR%2==1) print $0}' file

输出第一列和第7列相同内容的行

awk -F'\t' '{ if($1==$7){print $0} }' in.txt > out.txt

输出第一列和第7列除去空格后相同内容的行

需要对两列使用gsub函数去除空格然后比较。注意两点:

  1. 空格分半角' '和全角' ',两者不等同。
  2. print ori不要写成print $ori, 后者等同于print $0, 由于gsub改变了$1$7的值,所以$0的结果是被去除了空格。

    awk -F'\t' '{ ori=$0; gsub(/ /, "", $1);gsub(/ /, "", $7);if($1==$7){print ori} }' ./in

管道-命令结合

tail -n +2 file | awk '{print $1*$2}' #表示输出file中从第二行开始到结束的行,跳过首行的描述信息或注释等

tr -d ',-' < file | sed 's/^.../&-' #将file中的逗号与连字符删掉后在每行前三个字符与后边字符之间加上连字符

echo {1..10} | tr ' ' '\n' | awk '{print $1*2}' | xargs #xargs将多行的数据转成了单行,输出:2 4 6 8 10 12 14 16 18 20

执行单个awk脚本与用管道进行多个awk串联的比较

使用管道将多个命令串起来将整个任务分解开来无疑更容易理解处理思路,并且利用多CPU并行工作还可提高效率。

如下操作,对数字进行替换,两种方式的执行时间比较:

time seq 1 10000000 | sed -e 's/1/one/g' -e 's/0/zero/g' > /dev/null

V.S.

time seq 1 10000000 | sed 's/1/one/g' | sed 's/0/zero/g' > /dev/null

gawk进行正则表达式字符串提取

gawk 是 AWK 的 GNU 版本。gawk可能没有预装在系统中,需要额外安装。

用法:gawk 'match($0, pattern, ary) {print ary[1]}'

例子:

echo "abcdef" | gawk 'match($0, /b(.*)e/, a) {print a[1]}'

其中,a[1]表示括号中匹配的结果.

将a[1]替换成ary['${2:-'0'}']可以匹配整个字符串

输出: cd.

可以写成一个shell函数,方便调用:

function regex { gawk 'match($0,/'$1'/, ary) {print ary['${2:-'0'}']}'; }

使用: echo "abcdef" | regex 'b.*f'

sed、awk命令速查的更多相关文章

  1. awk命令速查

    awk与sed.grep一样都是为了加工数据流而做成的文本加工过滤器命令.awk会事先把输入的数据根据字段单位进行分割.在没有制定分割单位的情况下,以输入数据中的空格或Tab为分隔符.与sed相比,它 ...

  2. Linux常用命令速查备忘

    Linux常用命令速查备忘   PS:备忘而已,详细的命令参数说明自己man 一. 启动,关机,登入,登出相关命令 [login] 登录 [logout] 登出 [exit] 登出 [shutdown ...

  3. 简明 Git 命令速查表(中文版)

    原文引用地址:https://github.com/flyhigher139/Git-Cheat-Sheet/blob/master/Git%20Cheat%20Sheet-Zh.md在Github上 ...

  4. Linux命令速查手册,超详细Linux命令教程

    一.常用命令速查 ls cd pwd cat more less tail head cp scp mv mkdir rmdir touch rm ps kill top free clear tre ...

  5. 转收藏:Git常用命令速查表

    一. Git 常用命令速查 git branch 查看本地所有分支git status 查看当前状态 git commit 提交 git branch -a 查看所有的分支git branch -r ...

  6. Redis常用命令速查 02_转

    一.Key Key命令速查: 命令 说明 DEL 删除给定的一个或多个 key,不存在的 key 会被忽略,返回值:被删除 key 的数量 DUMP 序列化给定 key,返回被序列化的值,使用 RES ...

  7. Git 命令速查表

    Git 命令速查表 1.常用的Git命令 命令 简要说明 git add 添加至暂存区 git add-interactive 交互式添加 git apply 应用补丁 git am 应用邮件格式补丁 ...

  8. Git 常用命令速查表(图文+表格)

    一. Git 常用命令速查 git branch 查看本地所有分支git status 查看当前状态 git commit 提交 git branch -a 查看所有的分支git branch -r ...

  9. Linux常用命令速查-汇总篇

    Linux常用命令速查-用户管理 Linux常用命令速查-文件管理 Linux常用命令速查-系统监控 Linux常用命令速查-网络管理 Linux常用命令速查-定时任务 Linux常用命令速查-Vim

随机推荐

  1. C# 文件类中 File ,FileInfo 类的主要区别

    System.IO命名空间中提供的文件操作类有File和FileInfo,这两个类的功能基本相同,只是File是静态类,其中所有方法都是静态的,可以通过类名直接调用,不需要实例化.而FileInfo是 ...

  2. Web.sitemap网站导航

    全文注释: Web.sitemap导航XML文件,站点地图,功能实现菜单 1.xml的版本1.0 和编码utf-8 2.Url链接 Title显示的标题 Description描述(ToolTip) ...

  3. Java 环境

    1. Java 环境1999年发布第二代java平台 简称 Java2 标准版 Standard Edition J2SE 企业版 Enterprise Edition J2EE 微型版 Micro ...

  4. Description Resource Path Location Type Unknown Unknown Unknown org.eclipse.core.internal.resources.Marker is not of a displayable type

    是访问限制报错. 方法一: 全局属性Project>preferences>java>Compiler>Errors/Warnings>把右侧的[Deprecated a ...

  5. js实现用户输入日期算出是今年的第几天

    const rs = require("readline-sync"); // 根据用户输入的年月日输出第几天 // 欢迎 console.log("欢迎来到查询系统&q ...

  6. Jest did not exit one second after the test run has completed.

    使用 Jest 进行单元测试时出现如下问题: Jest did not exit one second after the test run has completed. This usually m ...

  7. 实战OpenGLES--iOS平台使用OpenGLES渲染YUV图片

    上一篇文章 实战FFmpeg--iOS平台使用FFmpeg将视频文件转换为YUV文件 演示了如何将视频文件转换为yuv文件保存,现在要做的是如何将yuv文件利用OpenGLES渲染展示出图像画面.要将 ...

  8. DBUtils模块

    Python 中的数据库连接池 DBUtils是Python的一个用于实现数据库连接池的模块. 有两种模式 模式一:为每个线程创建一个连接,线程即使调用了close方法,也不会关闭,只是把连接重新放到 ...

  9. 基于335X平台Linux交换芯片驱动开发

    基于335X平台Linux交换芯片驱动开发   一.软硬件平台资料 1.开发板:创龙AM3359核心板,网口采用RMII形式. 2.Kernel版本:4.4.12,采用FDT 3.交换芯片MARVEL ...

  10. Java--8--新特性--Optional--有效防止空指针异常

    Optional<T> 类(java.util.Optional) 是一个容器类,代表一个值存在或不存在,原来用 null 表示一个值不存在,现在 Optional 可以更好的表达这个概念 ...