awk命令-字符串过滤

awk 从第i列开始显示后面所有内容(以空格为分隔符)

awk -F ' ' '{ for(i=1; i<=3; i++){ $i="" };print $0}'

awk 过滤出批定单列

awk -F ' ' '{print $0}'	# 显示所有,不过滤
awk -F ' ' '{print $1}'	# 过滤出第一列
awk -F ' ' '{print $1,$3}'	# 过滤出第一、三列
awk -F ' ' '{print $NF}'	# 过滤出最后一列
awk -F ' ' '{print $(NF-2)}' # 过滤出倒数第三列(倒数第一列为0列)

查询大文件行数(该方法比wc -l FILENAME要快)

time awk 'END{print NR}'  FILENAME

过滤重复行

awk ' !x[$0]++' filename

简要解释一下:awk 的基本执行流程是,对文件的每一行,做一个指定的逻辑判断,如果逻辑判断成立,则执行指定的命令;如果逻辑判断不成立,则直接跳过这一行。 我们这里写的 awk 命令是!x[$0]++,意思是,首先创建一个 map 叫x,然后用当前行的全文$0作为 map 的 key,到 map 中查找相应的 value,如果没找到,则整个表达式的值为真,可以执行之后的语句;如果找到了,则表达式的值为假,跳过这一行。 由于表达式之后有++,因此如果某个 key 找不到对应的 value,该++操作会先把对应的 value 设成 0,然后再自增成 1,这样下次再遇到重复的行的时候,对应的 key 就能找到一个非 0 的 value 了。 我们前面说过,awk 的流程是先判断表达式,表达式为真的时候就执行语句,可是我们前面写的这个 awk 命令里只有表达式,没有语句,那我们执行什么呢?原来,当语句被省略的时候,awk 就执行默认的语句,即打印整个完整的当前行。就这样,我们通过这个非常简短的 awk 命令实现了去除重复行并保留原有文件顺序的功能。

过滤时同时指定多个分隔符

# 用:  < 或 > 做为分隔符,打印出第二列 
awk -F '[:<>]' filename '{print $2}'

# 示例文件
cat filename
	foo:bar<123
	baz:qux<456

# 用: 或 < 做为分隔符
awk -F '[:<]' '{print $2}' filename
	bar
	qux

当一行数据中同时存在多个分隔符时,awk 会按照指定的分隔符顺序依次处理每个分隔符,并将每个分隔符前后的文本作为一个字段处理。 例如,假设有一个文本文件 file.txt 包含如下数据:

foo:bar/baz|qux

如果使用如下命令:

awk -F '[:/|]' '{print $2}' file.txt

那么 awk 会按照冒号、斜杠和竖线的顺序处理每个分隔符,并将每个分隔符前后的文本作为一个字段处理。因此,输出结果为:

bar

因为 awk 遇到冒号后,将 foo 和 bar/baz|qux 分别作为第一个和第二个字段处理。然后,awk 在第二个字段中遇到了斜杠,将 bar 和 baz|qux 分别作为第二个和第三个字段处理。最后,在第三个字段中遇到了竖线,将 baz 和 qux 分别作为第三个和第四个字段处理。因此,输出结果为 bar。

因此,当一行数据中同时存在多个分隔符时,awk 会按照指定的分隔符顺序依次处理每个分隔符,并将每个分隔符前后的文本作为一个字段处理,不会以哪个分隔符为准。

运算符

执行cat /etc/shadow | awk -F: '($2 == "" ) { print $1}', 查看空密码账户

以下是一些常用的比较运算符:

#等于:`==`
awk '$1 == "pattern" {print $0}'

#不等于:`!=`
awk '$1 != "pattern" {print $0}'

#大于:`>`
awk '$1 > 10 {print $0}'

#小于:`<`
awk '$1 < 10 {print $0}'

#大于等于:`>=`
awk '$1 >= 10 {print $0}'

#小于等于:`<=`
awk '$1 <= 10 {print $0}'

#匹配正则表达式:`~`
awk '$1 ~ /pattern/ {print $0}'

#不匹配正则表达式:`!~`
awk '$1 !~ /pattern/ {print $0}'

类命令还有[[cut命令-截取字符串|cut命令]] [[grep命令-过滤字符串|grep命令]]

最后更新于