awk入门小记

作者:matrix 发布时间:2019年11月6日星期三 分类:command Linux

图片5055-awk入门小记

awk用于unix的文本处理,经常出现和使用。读取每一行文本进行格式化输出。

测试环境 Macos

awk简单操作

默认使用空格进行字符串分割

echo '1 2 3' |awk '{print $0}' # 1 2 3

echo '1 2 3' |awk '{print $3}' # 3

echo -e "1\n2\n3" |awk '/[23]/' #正则条件查找

echo -e "abc\n1a2\n33" |awk '/a/' #正则条件查找字母a 

awk '{print $3}' file_path #指定文件

ls -alh|awk '/^d/' #输出目录
# drwxr-xr-x    3 panc  staff    96B  7 16 23:32 pt-program

echo '1-2-3' |awk -F '-' '{print $2}' #指定分割符号 -  输出 2

$0表示当前行
$1表示第一个分割的字段

awk命令后面跟操作的语句字符串''包裹,每个语句段落用花括号{}包裹,语句段落中用分号;分隔语句。

echo -e '1 2 3\n4 5 6' |awk '{print $0;print("-end-")}'
echo -e '1 2 3\n4 5 6' |awk '{print $0;}{print("-end-")}'
#上面输出结果相同
#1 2 3
#-end-
#4 5 6
#-end-


echo -e '1 2 3\n4 5 6' |awk '{print $1,$3}'
#输出
#1 3
#4 6

使用内置变量

NF表示当前行有多少个分割字段

echo  '1-2-3' |awk -F '-' '{print $(NF)}' # 3  获取最后一个分割字符
echo  '1-2-3' |awk -F '-' '{print $(NF-1)}' # 2  获取倒数第二个分割字符

其他变量
NR表示当前处理的是第几行

BEGIN预处理

在执行处理之前提前设置一些信息
比如之前的-F参数可以使用BEGIN来设置

echo -e "a-b-c" |awk 'BEGIN{FS="-"} /^a/{print $0}' #设置分割符为-

echo -e "a-b-c" |awk 'BEGIN{FS="-";print "this title::"} {print $0}' #设置输出的首行标题

echo -e "1122\n3344" |awk 'BEGIN{FIELDWIDTHS="2 2";} {print $1,$2}' #固定字段宽度  (mac os中测试失败)
#输出
#11 22
#33 44

内置变量
FS字段分隔符
FIELDWIDTHS指定字段宽度
ORS指定输出的行分隔符

if逻辑处理

awk还可以支持函数和复杂的逻辑处理,完全可以在里面定义函数 调用 判断

例子:
显示红色error
绿色seccess
白色log


echo -e 'success\nerror\nsuccess\nloginfo' | awk \ '{ if (/error/) { print "\033[91m" $0 "\033[0m" } else if (/success/){ print "\033[32m" $0 "\033[0m"; }else{ print $0 } next; }'

上面语句有换行的段落方便阅览。一行简写也是可以
例子:
判断值大小

echo -e '12\n14\n232\n90' |awk '{if($0>=90) print $0}' #输出>=90的数据
#232
#90

for循环

使用for循环计算求和


echo '5' |awk '{ \ total = 0 for (var = 1; var < $0; var++) { total += var } print "total:",total }'

Built-In Functions函数使用

awk中语义中支持函数的使用

echo -e 'H htjim\nDot\ncom\n009' |awk '{print toupper($0)}'#转换为大写

内置函数
toupper 转换为大写
tolower 转换为小写
rand 随机数

其他函数参考手册:
https://www.gnu.org/software/gawk/manual/html_node/Built_002din.html#Built_002din

自定义函数

自定义彩色文字输出函数awk内部执行调用


echo -e 'success\nerror\nsuccess\nloginfo' | awk \ ' function red(s) { printf "\033[1;31m" s "\033[0m " } function green(s) { printf "\033[1;32m" s "\033[0m " } function blue(s) { printf "\033[1;34m" s "\033[0m " } { if (/error/) { print red($0) } else if (/success/){ print green($0) }else{ print blue($0) } }'

其他例子

结合tail -f log显示红色报错提示

 tail -f test.log |  awk '{
 if (/success/) {
 print "\033[91m" $0 "\033[0m"
 } else {
 print "\033[32m" $0 "\033[0m"; 
 }
 next;
}';

next用于直接跳到下一行文本进行执行 有点continue的意思

参考:
https://likegeeks.com/awk-command/

http://www.ruanyifeng.com/blog/2018/11/awk.html

https://www.cnblogs.com/Linuxprobe/p/5745381.html

记linux输出重定向操作>&

作者:matrix 发布时间:2019年10月19日星期六 分类:command Linux

今天看到2>&1>/dev/null 2>&1有点相似但又完全不同,一直都是CV方式来使用 仅知道后者用于禁止所有输出信息。

简单整理笔记

基本操作符号和数字描述符号

>用于输出覆盖内容,>>用于输出追加内容
<用于输入,<<用于设置输入结束符号
<<end:表示当输入end的时候结束输入操作

/dev/null表示Linux中的空设备,也当是数据黑洞,无限吞噬。

类型 文件描述符 默认情况 对应文件句柄位置
标准输入(standard input) 0 从键盘获得输入 /proc/self/fd/0
标准输出(standard output) 1 输出到屏幕(即控制台) /proc/self/fd/1
错误输出(error output) 2 输出到屏幕(即控制台) /proc/self/fd/2

输出内容重定向

command >/dev/null 2>&1

这样执行就不会有任何信息显示和保存

补充命令之后:

command 1>/dev/null 2>&1

说明:

>/dev/null等同于1>/dev/null 意思是 当前控制台的信息输出到空设备。

2>&1使用&符号将2重定向绑定到1,意思是将错误信息指向控制台,而这个时候的控制台又指向了空设备。

如果去掉&符号的2>1会导致错误信息输出到文件名为1里面。

linux执行命令时会按顺序从左到右读取来确定0,1,2这三个输入输出的位置。

command 2>&1 >/dev/null

把两个重定向的位置写反之后就是完全不同的意思。
等同于command 2>&1 1>/dev/null

linux执行命令到2>&1会将错误输出指向1即控制台,到这里就会完成错误输出(2)的位置确定。也就不会更改了。

执行到1>/dev/null会将标准输出(1)指向空设备,而此时的错误输出(2)已经确定位置了就不会发生更改。

所以最终错误信息显示到控制台,正常信息不会看到。

参考:
https://blog.csdn.net/zhaominpro/article/details/82630528
https://www.cnblogs.com/ultranms/p/9353157.html
https://blog.csdn.net/wz947324/article/details/80005224