linux awk搜索文本最后个字符串,Shell文本处理三剑客之awk

awk 是一个文本处理工具,通常用于处理数据并生成结果报告。其命名源于三位创始人姓氏首字母:Alfred Aho、Peter Weinberger、Brian Kernighan。

语法:awk [options] 'BEGIN{} pattern {commands} END{}' file

stdout | awk [options] 'BEGIN{} pattern {commands} END{}'

说明:options 选项

BEGIN{} 正式处理数据之前执行

pattern 匹配模式

{commands;...} 处理命令,可能多行

END{} 处理完所有匹配数据后执行

内置变量变量名说明$0整行内容

$1-$n当前行的第 1 - n 个字段(列)

NFNumber Field,当前行字段个数(多少列)

NRNumber Row,当前行的行号,从 1 开始计数

FNRFile Number Row,多文件处理时,每个文件行号单独计数,都是从 0 开始

FSField Separator,输入字段分隔符(默认空格或 tab 键)

RSRow Separator,输入行分隔符(默认回车换行)

OFSOutput Field Separator,输出字段分隔符(默认空格)

ORSOutput Row Separator,输出行分隔符(默认回车换行)

FILENAME当前输入的文件名字

ARGC命令行参数个数

ARGV命令行参数数组

示例:# 以 : 分隔,输出第 1 列

➜ awk 'BEGIN{FS=":"} {print $1}' /etc/passwd

# 以 -- 分隔成行,以 : 分隔成列,输出第 1、2 列

➜ awk 'BEGIN{FS=":";RS="--"} {print $1,$2}' /etc/passwd

# 以 : 分隔列,输出最后一列,因为 NF 变量是总列数

➜ awk 'BEGIN{FS=":"} {print $NF}' /etc/passwd

格式化输出(printf)格式符说明修饰符说明%s字符串-左对齐

%d十进制+右对齐

%f浮点数#八进制前面加 0,十六进制前面加 0x

%x十六进制

%o八进制

%e科学计数法

%c单个字符的 ASCII 码

示例:# printf "%+20s %-20s\n",$1,$7

# - 左对齐;+ 右对齐

# 20 列宽,不足则补空

# s 打印字符串

# .3f 打印保留 3 位数的浮点数

➜ awk 'BEGIN{FS=":";OFS="-"}{printf "%+20s %20.3f %-20s\n",$1,$3,$7}' /etc/passwd

root 0.000 /bin/bash

bin 1.000 /sbin/nologin

daemon 2.000 /sbin/nologin

adm 3.000 /sbin/nologin

lp 4.000 /sbin/nologin

模式匹配(pattern)RegExp:/patern/

关系运算:、<=、>=、==、!=、~ 正则匹配、!~ 非正则匹配、&& 与、|| 或、! 非

示例:# 打印以 root 开头的行

➜ awk 'BEGIN{FS=":"} /^root/ {print $0}' /etc/passwd

root:x:0:0:root:/root:/bin/bash

# 打印第 3 列大于 1000 的行

➜ awk 'BEGIN{FS=":"} $3>1000 {print $0}' /etc/passwd

nfsnobody:x:65534:65534:Anonymous NFS User:/var/lib/nfs:/sbin/nologin

# 打印第 7 列是 /sbin/nologin 的行

➜ awk 'BEGIN{FS=":"} $7=="/sbin/nologin" {print $0}' /etc/passwd

bin:x:1:1:bin:/bin:/sbin/nologin

daemon:x:2:2:daemon:/sbin:/sbin/nologin

# 打印第 7 列以 nologin 结尾的行

➜ awk 'BEGIN{FS=":"} $7~/.*nologin$/ {print $0}' /etc/passwd

bin:x:1:1:bin:/bin:/sbin/nologin

daemon:x:2:2:daemon:/sbin:/sbin/nologin

# 打印第 3 列大于 500,并且第 7 列以 nologin 结尾的行

➜ awk 'BEGIN{FS=":"} $3>500 && $7~/.*nologin$/ {print $0}' /etc/passwd

chrony:x:997:995::/var/lib/chrony:/sbin/nologin

dockerroot:x:996:993:Docker User:/var/lib/docker:/sbin/nologin

计算表达式

示例:# 数学计算

➜ awk 'BEGIN{x=10;y=2; print x+y}'

12

➜ awk 'BEGIN{x=10;y=2; print x*y}'

20

➜ awk 'BEGIN{x=10;y=2; print x^y}'

100

➜ awk 'BEGIN{x=10;y=2; print x**y}'

100

➜ awk 'BEGIN{x=10;y=x++; print x,y}'

11 10

➜ awk 'BEGIN{x=10;y=++x; print x,y}'

11 11

# 打印空行行号、统计空行数量

➜ awk 'BEGIN{idx=0;} /^$/ {idx++; print NR} END{print idx;}' /etc/passwd

流程控制语句

语法:# 条件判断

if(condition1) {

# do something

} else if(condition2) {

# do something

} else {

# do something

}

# 循环

while(condition) {

#do something

}

do

# do something

while(condition)

for(i=0;i<10;i++) {

# do something

}

示例:# 如果第 3 列小于 10 并且第 7 列是 /sbin/nologin 的行打印 this is if

# 如果第 3 列大于 500 的打印 this is else if

# 否则打印 this is else

➜ awk 'BEGIN{FS=":"} { if($3<10 && $7="/sbin/nologin") {print "this is if"} else if($3>500) {print "this is else if"} else {print "this is else"}}' /etc/passwd

this is if

this is if

this is else

this is else if

this is else

# 计算 1-10 相加的结果

# 注意:变量不需要提前声明

➜ awk 'BEGIN{ while(i<10) { sum+=i; i++}; print sum}'

45

➜ awk 'BEGIN{do { sum+=i; i++; } while(i<10); print sum}'

45

➜ awk 'BEGIN{ for(i=0;i<10;i++) { sum+=i; }; print sum}'

45

字符串函数函数名说明返回值length(str)计算字符串长度整数长度值

index(str,sub_str)在 str 中查找 sub_str 的位置位置索引,从 1 计数

tolower(str)转小写转换后的小写字符串

toupper(str)转大些转换后的大写字符串

substr(str,start,length)从 str 第 start 个字符开始,截取 length 位截取后到子串

split(str,arr,fs)按 fs 拆分字符串,结果保存到 arr拆分后子串的个数

match(str,reg)在 str 中按 reg 查找,返回位置索引位置

sub(reg,new_sub_str,str)在 str 中搜索符合 reg 的子串,将其替换为 new_sub_str,只替换第一个替换的个数

gsub(reg,new_sub_str,str)类似 sub,替换所有替换的个数

示例:# sub(/oo/,"11",$1) 返回替换的个数;后面的 $1 为替换后的值

➜ awk 'BEGIN{FS=":"} { print length($1),toupper($1),substr($1,0,2),sub(/oo/,"11",$1),$1}' /etc/passwd

4 ROOT ro 1 r11t

3 BIN bi 0 bin

6 DAEMON da 0 daemon

4 SYNC sy 0 sync

# 数组下标从 1 开始

➜ awk 'BEGIN{str="Shell;Python;C;C++;Java;PHP"; split(str,arr,";"); print arr[2]}'

Python

➜ awk 'BEGIN{str="Shell;Python;C;C++;Java;PHP"; split(str,arr,";"); for(i in arr) { print arr[i]; }}'

C++

Java

PHP

Shell

Python

C

常用选项(options)-v 参数传递

-f 指定脚本文件

-v 指定分隔符

-V 查看 awk 版本

示例:# 引入外部变量

➜ var1=10

➜ var2="hello awk"

➜ awk -v var1="$var1" -v var2="$var2" 'BEGIN{print var1,var2}'

10 hello awk

# 把所有操作抽离到一个独立文件

# 建议:复杂操作优先使用这种方式,更易于程序理解和管理

➜ touch script.awk

BEGIN{

FS=":"

}

{

if($3<10 && $7="/sbin/nologin") {

print "this is if"

} else if($3>500) {

print "this is else if"

} else {

print "this is else"

}

}

➜ awk -f script.awk /etc/passwd

# -F: 相当于 BEGIN{FS=":"}

$ awk -F: '{print $1}' pwd

root

bin

daemon

数组

shell 中的数组操作如下:操作示例输出定义一个数组arr=("Python" "PHP" "Java" "Go" "Rust")

某个数组元素(下标从 0 开始)echo ${arr[2]}Java

数组元素个数echo ${#arr[@]}5

某个元素的长度echo ${#arr[0]}6

修改元素值arr[2]="JAVA"

删除数组元素unset arr[1]

打印所有数组元素)echo ${arr[@]}Python JAVA Go Rust

分片访问echo ${arr[@]:0:2}Python JAVA

数组元素替换(找到的第一个)echo ${arr[@]/A/a}Python JaVA Go Rust

数组元素替换(所有)echo ${arr[@]//A/a}Python JaVa Go Rust

数组遍历for a in ${arr[*]}; do echo $a; done而 awk 中数组的使用略有不同,它使用关联数组提供数组功能,即数组的索引可以是数字或任意字符串。

语法示例:# 定义

# 语法:array_name[index]=value

➜ awk 'BEGIN{arr[0]=0; arr["second"]="2"; print arr[0],arr["second"];}'

0 2

# 数组元素参与计算

➜ awk 'BEGIN{arr[0]=0; arr["second"]="2"; print arr[0]+3,arr["second"];}'

3 2

# 删除数组元素

# 语法:delete array_name[index]

➜ awk 'BEGIN{arr[0]=0;arr["second"]="2"; delete arr["second"]; print arr["second"];}'

# 遍历数组

# 方式一:for ... in 是无序输出

➜ awk 'BEGIN{str="Python Rust PHP Go"; arrLen=split(str,arr," "); for(i in arr){ print i,arr[i] }}'

4 Go

1 Python

2 Rust

3 PHP

# 方式二:for(i=1;i<=len;i++) { ... } 有序输出

➜ awk 'BEGIN{str="Python Rust PHP Go"; arrLen=split(str,arr," "); for(i=1;i<=arrLen;i++){ print i,arr[i] }}'

1 Rust

2 Go

3 Python

4 PHP

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值