awk
是一个强大的文本处理工具,主要用于对结构化数据进行模式扫描和处理。它支持复杂的操作和脚本编写,能够进行模式匹配、文本处理、数据报告生成等。
awk的功能:
字符串处理和替换;
数据统计和报告生成;
复杂的条件判断和循环处理;
数据格式转换。
基本格式
awk [选项参数] 'pattern {action}' file
参数说明:
1)pattern
:匹配的模式,支持正则表达式。
2)action
:在匹配模式的行上执行的操作。
3)常用选项参数:
参数 | 说明 |
---|---|
-F fs | 指定输入字段分隔符,默认是空格或制表符 |
-v var=value | 为awk 程序中的变量赋初值 |
-f program-file | 从指定文件读取awk 程序 |
4)常见的内置变量:
内置变量 | 说明 |
---|---|
$0 | 表示完整的输入记录 |
$n | 表示指定分隔符后,当前指定的第n个字段 |
FS | 表示字段输入分隔符,默认以空格为分隔符 |
OFS | 表示字段输出分隔符 |
NF | 表示字段的个数,即以分隔符分割后,当前行一共有多少个字段 |
NR | 表示当前记录数,即行数 |
常用命令举例
假设有一个file.txt文件,内容如下:
name,age,sex,salary
Alice,30,女,9000
Bob,25,男,8000
Carol,35,男,7000
Karry,21,女,5000
1.基本示例
# 打印文件file.txt的每一行
awk '{ print }' file.txt
2.指定字段分隔符
假设文件内容用逗号分隔,打印第1、第3个字段。(其中 -F ',' 可以直接简写成-F,)
awk -F ',' '{ print $1, $3 }' file.txt
3.使用模式匹配
# 打印包含“Karry”字符串的行
awk '/Karry/ { print }' file.txt
4.按条件过滤
# 打印第2列字段(age)大于30的人的姓名
awk -F ',' '$2 > 30 { print $1 }' file.txt
5.使用变量
# 为变量age赋值并使用
awk -F ',' -v age=30 '$2 > age { print $0 }' file.txt
6.BEGIN和END块
BEGIN
块在处理任何输入行之前执行。
END
块在处理完所有输入行后执行。
# 计算file.txt文件中第4列字段(工资)的总和
awk -F ',' 'BEGIN { sum=0 } { sum += $4 } END { print sum }' file.txt
7.使用-f
选项从脚本文件中读取程序
1)创建一个名为script.awk
脚本文件
vim script.awk
并将以下内容写入脚本文件中:
#!/usr/bin/awk -f
# 使用逗号作为字段分隔符
BEGIN { FS = "," }
# 打印第1和第3字段
{ print $1, $3 }
详细说明:
脚本文件头部:
#!/usr/bin/awk -f
指定用awk
解释器来运行这个脚本文件。BEGIN 块:
BEGIN { FS = "," }
设置字段分隔符为逗号。主代码块:
{ print $1, $3 }
打印每行的第1和第3字段。
保存文件并关闭编辑器:wq!2)运行awk脚本文件(有两种方式)方式一:直接用 awk
命令来执行这个脚本
awk -f script.awk file.txt
方式二:授权脚本文件具有可执行权限,然后运行脚本文件
# 确保脚本文件具有可执行权限:
chmod +x script.awk
#运行脚本文件,并指定输入文件:
./script.awk file.txt
8. 格式转换
# 将file.txt文件格式转换为TSV(Tab Separated Values)格式
awk 'BEGIN { FS=","; OFS="\t" } { $1=$1; print }' file.txt
说明:
**
BEGIN { FS=","; OFS="\t" }
**:在处理开始时,将输入字段分隔符设置为逗号,将输出字段分隔符设置为制表符。**
$1=$1; print
**:通过赋值操作强制awk
重新解析字段,然后输出。
9.提取并格式化指定列
# 假设想提取 `Name` 和 `Age` 列,并格式化输出为 "Name: Age years old"
awk -F ',' '{ print "Name: " $1 ", Age: " $2 " years old" }' file.txt
10.转换为JSON格式
将file.txt文件转换为JSON格式:
awk -F, 'NR==1 {
for (i=1; i<=NF; i++) header[i]=$i;
next
} {
printf("{");
for (i=1; i<=NF; i++) {
printf("\"%s\":\"%s\"", header[i], $i);
if (i<NF) printf(", ");
}
printf("}\n");
}' file.txt
11.转换为HTML表格
将file.txt转换为HTML表格:
awk -F, 'BEGIN {
print "<table border=\"1\">";
print "<tr><th>Name</th><th>Age</th><th>Gender</th></tr>";
}
NR>1 {
printf("<tr>");
for (i=1; i<=NF; i++) printf("<td>%s</td>", $i);
printf("</tr>\n");
}
END {
print "</table>"
}' file.txt