linux学习:sed与awk与tr用法整理

流编辑器:sedphp

语法:sed [-hnV][-e<script>][-f<script文件>][文本文件]

参数:linux

  • -e<script>或--expression=<script> 以选项中指定的script来处理输入的文本文件。
  • -f<script文件>或--file=<script文件> 以选项中指定的script文件来处理输入的文本文件。
  • -h或--help 显示帮助。
  • -n或--quiet或--silent 仅显示script处理后的结果。
  • -V或--version 显示版本信息。

动做:git

  • a :新增, a 的后面能够接字串,而这些字串会在新的一行出现(目前的下一行)~
  • c :取代, c 的后面能够接字串,这些字串能够取代 n1,n2 之间的行!
  • d :删除,由于是删除啊,因此 d 后面一般不接任何咚咚;
  • i :插入, i 的后面能够接字串,而这些字串会在新的一行出现(目前的上一行);
  • p :打印,亦即将某个选择的数据印出。一般 p 会与参数 sed -n 一块儿运行~
  • s :取代,能够直接进行取代的工做哩!一般这个 s 的动做能够搭配正规表示法!例如 1,20s/old/new/g 就是啦!

例子:
sed 's/pattern/replace_string/' file    #从给定文本中的字符串利用正则表达式进行匹配并替换每一行中第一次符合样式的内容
sed 's/text/replace/' file > newfile    #替换每一行中第一次符合样式的内容并将替换结果重定向到新文件
sed -i 's/test/replace/' file        #参数-i使用替换每一行中第一次符合样式的内容结果应用于源文件
sed 's/pattern/replace_string/g' file     #后缀/g意味着会替换每一处匹配,而不是每一行中第一次匹配正则表达式

sed -i "s/原字符串/新字符串/g" `grep 原字符串 -rl ./`     #将当前目录及子目录下全部包含“原字符串” 的文件的行所有替换成“新字符串”shell

sed -i 's/max_execution_time = 30/max_execution_time = 300/g'  /etc/php/php.ini    #修改php配置文件的配置
sed 's:test:rep;ace:g'          #使用:替换/,这两个符号都是定界符,用其余符号也无所谓,可是当定界符在匹配的样式内部时,须要加\进行转义
sed 'expression; expression'        #组合多个表达式
sed '/^$/d' file             #移除空白行,^$表示空白行,/d表示将匹配的样式移除
echo thisthisthisthis | sed 's/this/THIS/2g'   #后缀/2g表示从第2处开始(包括第二次)开始匹配。第N处,就使用/Ng。结果:thisTHISTHISTHIS
cat file | sed 's/pattern/replace_string/' file    #从stdin中读取输入并替换每一行中第一次符合样式的内容
echo this is an example | sed 's/\w\+/[&]/g'     #符号&表示已匹配的字符串。正则表达式\w\+匹配每个单词,并用[&]替换它,结果:[this] [is] [an] [example]
echo this is digit 7 in a number | sed '/digit \([0-9]\)/\l/' #参数\1(数字1)将digit 7转换为7express

---------------------------------------------------------------
text=hello
echo hello world | sed "s/$text/Hello/"    #输出结果HELLO world
---------------------------------------------------------------
文本混乱与恢复正常(替换空格,换行符,制表符等)
cat test.js | sed 's/;/;\n/g; s/{/{\n\n/g; s/}/\n\n}/g'        # s/;/;\n/g将;替换为\n; s/{/{\n\n/g将{替换为{\n\n s/}/\n\n/g将}替换为\n\n}
cat test.js | sed 's/;/;\n/g' |sed 's/{/{\n\n/g' | sed 's/}/\n\n}/g'   #同上
sed 's/ [^.]*mobbile phones[^.]*\.//g' test.txt      #移除文件test.txt中包含单词“mobile phones”的句子json

 sed -i "s/被替换的字符串/新字符串/g" `grep 被替换的字符串 -rl ./`    #整个目录下全局搜索替换


数据流工具:awk数组

语法

awk [选项参数] 'script' var=value file(s)  awk [选项参数] -f scriptfile var=value file(s)

选项参数:编辑器

    • -F fs or --field-separator fs
      指定输入文件折分隔符,fs是一个字符串或者是一个正则表达式,如-F:。
    • -v var=value or --asign var=value
      赋值一个用户定义变量。
    • -f scripfile or --file scriptfile
      从脚本文件中读取awk命令。
    • -mf nnn and -mr nnn
      对nnn值设置内在限制,-mf选项限制分配给nnn的最大块数目;-mr选项限制记录的最大数目。这两个功能是Bell实验室版awk的扩展功能,在标准awk中不适用。
    • -W compact or --compat, -W traditional or --traditional
      在兼容模式下运行awk。因此gawk的行为和标准的awk彻底同样,全部的awk扩展都被忽略。
    • -W copyleft or --copyleft, -W copyright or --copyright
      打印简短的版权信息。
    • -W help or --help, -W usage or --usage
      打印所有awk选项和每一个选项的简短说明。
    • -W lint or --lint
      打印不能向传统unix平台移植的结构的警告。
    • -W lint-old or --lint-old
      打印关于不能向传统unix平台移植的结构的警告。
    • -W posix
      打开兼容模式。但有如下限制,不识别:/x、函数关键字、func、换码序列以及当fs是一个空格时,将新行做为一个域分隔符;操做符**和**=不能代替^和^=;fflush无效。
    • -W re-interval or --re-inerval
      容许间隔正则表达式的使用,参考(grep中的Posix字符类),如括号表达式[[:alpha:]]。
    • -W source program-text or --source program-text
      使用program-text做为源代码,可与-f命令混用。
    • -W version or --version
      打印bug报告信息的版本。

工做方式:函数

awk 'BEGIN{ PRINT "start" } pattern { commands } END{print "END" } file

首先执行BEGIN语句块,而后从文件或stdin中读取一行,而后执行pattern{ commands }。直到文件所有读取完毕。读到输入流末尾时,执行END{ commands } 语句块。三个语句块都是可选的。若是没有提供pattern语句块则默认打印每个读取到行。


awk的特殊变量:
NR:表示记录数量,在执行过程当中对应于当前行号。
NF:表示字段数量,在执行过程当中相对于当前行的字段数。
$NF:表示当前行的最后一个字段。$(NF-1)表示当前行的倒数第二个字段。依次类推
$0:这个变量包含执行过程当中当前行的文本内容。
$1:这个变量包含第一个字段的文本内容。
$2:这个变量包含第二个字段的文本内容。依次类推。

FNR :与NR相似,不过多文件记录不递增,每一个文件都从1开始
\t:制表符
\n :换行符
FS:BEGIN时定义分隔符
RS: 输入的记录分隔符, 默认为换行符(即文本是按一行一行输入)
~ :匹配,与==相比不是精确比较
!~:不匹配,不精确比较
==:等于,必须所有相等,精确比较
!= :不等于,精确比较
&&:逻辑与
||:逻辑或
+:匹配时表示1个或1个以上
/[0-9][0-9]+/ :两个或两个以上数字
/[0-9][0-9]*/ :一个或一个以上数字
FILENAME:文件名
OFS:输出字段分隔符, 默认也是空格,能够改成制表符等
ORS :输出的记录分隔符,默认为换行符,即处理结果也是一行一行输出到屏幕
-F'[:#/]':定义三个分隔符
 
例子:

awk 'BEGIN { i=0 } { i++ } END{ print i }' filename    #逐行读取文件并打印行数
echo -e "line1\nline2" | awk 'BEGIN{ print "Start" } { print } END { print "END" } '
echo | awk '{ var1="v1"; var2="v2"; var3="v3"; print var1"-"var2"-"var3;}'
echo -e "line1 f2 f3\nline2 f4 f5\nline3 f6 f7" | awk '{ print "Line no:"NR",No of fields:"NF, "$0="$0,"$1="$1,"$2="$2,"$3="$3 }'
awk '{ print $3,$2 }' file   #打印文件中每一行的第2和第3个字段。
awk 'END{ print NR }' file   #统计文件中的行数,只加END语句块表示文件执行到最后一行时再输出行号
awk 'NR < 5' file          #打印文件中行号小于5的行
awk 'NR==2,NR==5' file    #打印文件中行号在2到5之间的行
awk '/linux/' file        #打印文件中包含样式linux的行(样式能够使用正则表达式)
awk '1/linux/' file        #打印文件中不包含包含样式linux的行
awk -F: '{ print $NF }' /etc/passwd #读取并打印/etc/passwd文件的内容,设置定界符为":",默认的定界符为空格
var1='test'; var2='text'                #(1)外部变量
echo | awk '{ print v1,v2 } v1=$var1 v2=var2     #(2)打印多个从标准输入传给awk的外部变量
awk '{ print v1,v2 }' v1=$var1 v2=var2 filename #(3)输入来自文件
cat test.txt | getline output             #将cat的输出读入变量output中。
awk 'BEGIN { FS=":" } { print $NF }' /etc/passwd #BEGIN语句块中则使用FS="delimiter"设置输出字段的定界符
awk '{arr[$1]+=1 }END{for(i in arr){print arr[i]"\t"i}}' FILE_NAME | sort -rn    #统计每一个单词的出现频率并排序
seq 5 | awk 'BEGIN{ sum=0;print "Summation:" } { print $1"+"; sum+=$1 } END{ print "=="; print sum }'    #将每一行第一个字段的值按照给定形式进行累加
echo | awk '{ "grep root /etc/passwd" | getline cmdout; print cmdout }'    #经过getline将外部shell命令的输出读入变量cmdout。变量cmdout包括命令grep root /etc/passwdde 的输出,而后打印包含root的行。

awk中使用循环与awk的内建函数
for(i=0;i<10;i++){ print $i; } 或者 for( i in array ) { print array[i]; }
length(string):返回字符串的长度
index(string ,search_string):返回search_string在字符串中出现的位置。
split(string, array, delimiter):用界定符生成一个字符串列表,并将该列表存入数组
substr(string, start-position, end-position):在字符串中用字符起止偏移量生成子串,并返回该子串。
sub(regex, replacement_str, string):将正则表达式匹配到的第一处内容替换成replacement_str。
gsub(regex, replacement_str, string):将正则表达式匹配到的全部内容替换成replacement_str。
match(regex ,string):检查正则表达式是不可以匹配字符串,若能,返回非0值;不然,返回0.

awk '{print $1}' access.log |sort|uniq -c|sort -nr|head -10   #分析access.log得到访问前10位的ip地址

awk -F '[,:]' '{if($6==140) print $0;}' test.log   #对test.log中每行用“,”和“:”分割,并打印出分割后第6个字段等于140的行

cat *_login.log | awk -F[,:] '{if($24<1541260800) print $24;}' | wc -l   #统计全部login日志中时间戳(拆分后第24个字段)小于1541260800的行数

awk -F: '{print $15}' test.log | awk -F, '{print $1}' | awk '{for(i=0;i<NF;i++) sum+=$i;}END{print sum}'   #对test.log的json行先用“:”分割再用“,”分割,再对某个字段累加

awk -F, '{print $14}' test.log | awk -F: '{print $2}' | awk '{for(i=0;i<NF;i++) sum+=$i;}END{print sum}'   #对test.log的json行先用“,”分割再用“:”分割再对某个字段累加

awk -F '[,:]' '{print $28}' test.log | awk '{for(i=0;i<NF;i++) sum+=$i;}END{print sum}'   #对test.log的json行分别用“,”和“:”分割后再对某个字段累加

awk -F[:,] '{print $28;}' pay.log | awk -F\" '{print $2;}' | awk '{for(i=0;i<NF;i++) sum+=$i;}END{print sum}'    #做用同上,在拆分后字段还包含双引号的状况下,再次拆分,获取数字再累加

---------------------------------------------------------------------------------------------------------------------------------------

文件:test.log 内如以下:

{"sid":1,"cid":1,"channel":140,"zid":0,"uid":"140524293334","role_id":"100252","goods_id":7,"cny":110000,"eventtime":1540244075}

{"sid":1,"cid":1,"channel":140,"zid":0,"uid":"140524293334","role_id":"100252","goods_id":7,"cny":120000,"eventtime":1540244075}

命令:

awk -F ':' '{print $9}' test.log | awk -F ',' '{print $1}'    #先使用 “:”为分隔符分割test.log每一行,而后获取第9个字段,再用“,”为分隔符分割字符串,再取第一个字段。

结果:

110000

120000

如果要统计该字段的累加数:

awk -F ':' '{print $9}' test.log | awk -F ',' '{print $1}' | awk '{for(i=1;i<=NF;i++) sum+=$i;} END{print sum}'

结果:

230000

----------------------------------------------------------------------------------------------------------------------------------------

 


替换工具:tr

语法

tr [-cdst][--help][--version][第一字符集][第二字符集] tr [OPTION]…SET1[SET2]

参数:

  • -c, --complement:反选设定字符。也就是符合 SET1 的部份不作处理,不符合的剩余部份才进行转换
  • -d, --delete:删除指令字符
  • -s, --squeeze-repeats:缩减连续重复的字符成指定的单个字符
  • -t, --truncate-set1:削减 SET1 指定范围,使之与 SET2 设定长度相等
  • --help:显示程序用法信息
  • --version:显示程序自己的版本信息

例子:

echo 12345 | tr '0-9' '9876543210' #加密echo 87654 | tr '9876543210' '0-9' #解密echo "Hello 123 world 456" | tr -d '0-9' #使用-d将stdin中的数字删除并打印出来cat test.txt | tr -d '0-9' #同上echo "hello 1 char 2 next 3 " | tr -d -c '0-9 \n' #参数-c是使用补集。删除stdin中的全部数字和换行符以外的字符(这些字符是'0-9 \n'这个集合的补集)echo "this is a test !" | tr -s ' ' #参数-s压缩多个空格为单个------------------------------------------------tr能够像使用集合同样使用各类不一样的字符类:alnum:字母和数字alpha:字母cntrl:控制(非打印)字符digit:数字graph:图形字符lower:小写字母print:可打印字符punct:标点符号space;空白字符upper:大写字母xdigit:十六进制字符使用方式:tr [:class:] [:class:]例如:tr '[:lower:]' '[:upper:]' #将全部小写字母换成大写字母----------------------------------------------------

相关文章
相关标签/搜索