shell/awk/awk-数组与函数.md
2025-03-30 13:46:10 +08:00

5.2 KiB
Raw Permalink Blame History

awk 数组与函数


一:数组

awk可以使用关联数组这种数据结构,索引可以是数字或字符串。

awk关联数 组也不需要提前声明其大小,因为它在运行时可以自动的增大或减小。

1. 语法格式

array_name[index]=value
  • array_name数组的名称
  • index数组索引
  • value数组中元素所赋予的值

2. 创建数组

定义了一个站点(sites)数组,该数组的索引为网站英文简称,值为网站访问地址。

[root@wxin ~]# awk 'BEGIN {
sites["qfedu"]="www.qfedu.com";
sites["google"]="www.google.com"
print sites["qfedu"] "\n" sites["google"]
}'
www.qfedu.com
www.google.com

3. 访问数组

访问数组元素语法格式

array_name[index] 

访问数组元素

[root@wxin ~]# awk -F: '{username[++i]=$1} END{print username[1]}' /etc/passwd
root
[root@wxin ~]# awk -F: '{username[i++]=$1} END{print username[1]}' /etc/passwd 
bin
[root@wxin ~]# awk -F: '{username[i++]=$1} END{print username[0]}' /etc/passwd 
root

按元数个数遍历

[root@wxin ~]# awk -F: '{username[x++]=$1} END{for(i=0;i<x;i++) print i,username[i]}' /etc/passwd
0 root
1 bin
2 daemon
3 adm
4 lp
5 sync
6 shutdown
7 halt

[root@wxin ~]# awk -F: '{username[++x]=$1} END{for(i=1;i<=x;i++) print i,username[i]}' /etc/passwd
1 root
2 bin
3 daemon
4 adm
5 lp
6 sync
7 shutdown
8 halt
9 mail
10 operator

按索引遍历

[root@wxin ~]# awk -F: '{username[x++]=$1} END{for(i in username) {print i,username[i]} }' /etc/passwd
17 sshd
4 lp
18 postfix
5 sync
19 mysql
6 shutdown
7 halt
8 mail
9 operator
10 games
20 nginx

[root@wxin ~]# awk -F: '{username[++x]=$1} END{for(i in username) {print i,username[i]} }' /etc/passwd
17 tss
4 adm
18 sshd
5 lp
19 postfix
6 sync
7 shutdown
8 halt
9 mail
10 operator
20 mysql
11 games

# 注变量i是索引

4. 删除元素

删除数组元素语法格式

delete array_name[index]

删除数组元素

删除数组中的 google 元素(删除命令没有输出):

[root@wxin ~]# awk 'BEGIN {
sites["qfedu"]="www.qfedu.com";
sites["google"]="www.google.com"
delete sites["google"];
print fruits["google"]
}'

5. 多维数组

AWK 本身不支持多维数组,不过我们可以很容易地使用一维数组模拟实现多维数组。

如下示例为一个 3x3 的三维数组:

100 200 300
400 500 600
700 800 900

实例中array0 存储 100array0 存储 200 ,依次类推。

要在 array0 处存储 100, 使用: array["0,0"] = 100。

使用 0,0 作为索引,这并不是两个索引值,而是一个字符串索引 0,0。

模拟二维数组

[root@wxin ~]# awk 'BEGIN {
array["0,0"] = 100;
array["0,1"] = 200;
array["0,2"] = 300;
array["1,0"] = 400;
array["1,1"] = 500;
array["1,2"] = 600;
# 输出数组元素
print "array[0,0] = " array["0,0"];
print "array[0,1] = " array["0,1"];
print "array[0,2] = " array["0,2"];
print "array[1,0] = " array["1,0"];
print "array[1,1] = " array["1,1"];
print "array[1,2] = " array["1,2"];
}'

array[0,0] = 100
array[0,1] = 200
array[0,2] = 300
array[1,0] = 400
array[1,1] = 500
array[1,2] = 600

在数组上可以执行很多操作,比如,使用 asort 完成数组元素的排序,或者使用 asorti 实现数组索引的排序等等。

二:函数

awk的函数有许多除了系统自带的内建函数还有就是用户自定义的函数。

AWK 常用的函数

rand()            # 返回0 和1 之间一个随机数
srand()			  # 生成随机数种子
int()			  # 取整数
length([s])		  # 返回指定字符串的长度
sub(r,s,[t])	  # 对t字符串进行搜索r表示的模式匹配的内容并将第一个匹配的内容替换为s
gsub(r,s,[t])	  # 对t字符串进行搜索r表示的模式匹配的内容并全部替换为s所表示的内容
split(s,array,[r])# 以r为分隔符切割字符串s并将切割后的结果保存至array 所表示的数组中第一个索引值为1, 第二个索引值为2,…也就是说awk的数组下标是从1开始编的
substr(s,i,[n]) # 从s所表示的字符串中取子串取法从i表示的位置开始取n个字符。
systime()		  # 取当前系统时间,结果形式为时间戳。
system()		  # 调用shell中的命令。空格是awk中的字符串连接符如果system中需要使用awk中的变量可以使用空格分隔或者说除了awk的变量外其他一律用""引用起来。

自定义函数示例

function fname ( arg1,arg2 , ... ) {
statements
return expr
}
  • fname为函数名
  • arg1...为函数的参数,
  • statements是动作语言
  • return expr为由 statements 的结果从而决定最终函数所显示的内容。

自定义函数示例

[root@wxin ~]# cat fun.awk
    function max(v1,v2) {
        v1>v2?var=v1:var=v2
        return var
    }
      BEGIN{a=3;b=2;print max(a,b)}
awk f fun.awk