【linux之find及awk】

一、find命令

find

精确查找,根据提供的条件或组合条件进行查找,遍历所有文件,因此速度比较慢。

语法:

find 目录 条件 动作

默认目录是当前目录
默认条件是所有条件
默认动作是显示查找到的信息

 

条件(选项):

   -name FILENAME:精确匹配,根据文件名进行查找,文件名支持通配符
   -user USENAME:根据文件的属主查找文件
   -group GROUPNAME:根据文件的属组查找文件
   -nouser:查找没有对应属主用户的文件
   -nogroup:查找没有对应属组的文件
   -a:与
   -o:或
   -not:非
   find / -not \( -name passwd -a -user root \)

   -inum n:查看inode号为n的所有文件名
   时间单位为天
   -atime +|-n 访问时间
   -ctime +|-n 改变时间
   -mtime +|-n 修改时间
   时间单位为分钟
   -amin +|-n
   -cmin +|-n
   -mmin +|-n
   
   +10:10天前
   -10:10天内
   
   -mtime +60:60天前修改过
   -mtime -60:60天内修改过
   -mtime 60:60前同一时间修改
   -type c
              File is of type c:

              b      block (buffered) special

              c      character (unbuffered) special

              d      directory

              p      named pipe (FIFO)

              f      regular file

              l      symbolic link; this is never true if the -L option or the -follow option is in  effect,
                     unless  the  symbolic link is broken.  If you want to search for symbolic links when -L
                     is in effect, use -xtype.

              s      socket
   -maxdepth 2:查找两级子目录(放最前面)
   -perm(权限)-mode(与):查找所有的权限都必须满足mode条件的文件
                /mode(或):查找至少一个权限位满足mode条件的文件
find /tmp -perm -222 (三个条件必须同时具备)
find /tmp -perm /222(其中一个条件具备即可)

 

动作:

   -print:显示
   -exec:执行相应的命令,在执行命令之前向用户不询问
      {}:通过find命令查找到的文件名
   -exec COMMAND {} \;
   -ok:执行相应的命令。在执行之前向用户发出询问
   -ls:在执行查找之后以ls -l命令显示查找到的文件

 

find练习

  1)查找/var目录下属主为root,属组为mail的所有文件;
  find /var -user root -a -group mail
  2)查找/usr目录下不属于root、bin、qhdlink等用户的文件;
  useradd qhdlink
  find /usr -not \( -user root -a -user bin -a -user qhdlink \)
  3)查找/etc目录下最近一周内内容修改过且不属于root及student用户的文件;
  find /etc -mtime -7 -a -not -user root -a -not -user student
  4)查找当前系统上没有属主或属组且最近1天内曾被访问过的文件,并将其属主属组均修改为root;
  find / -nouser -o -nogroup -a -atime -1 -exec chown root: {} \;
  5)查找/etc目录下所有用户都没有写权限的文件,显示出其详细信息;
  find /etc -not -perm /222 -ls

 

二、awk

awk是一种可以处理数据、产生格式化报表的语言,功能相当强大。awk的工作方式是读取数据文件,将每一行数据视为一条记录(record),每笔记录以字段分隔符分成若干字段,然后输出各个字段的值。

以下是执行ps auxw的输出片段:

USER PID %CPU %MEM VSZ RSS TTY
STAT START TIME COMMAND
root 1 0.0 0.0 164 92 ?
Ss Apr09 0:01 init [5]

像这种固定结构的数据,用awk来处理,特别有威力,通常只要短短几行程序代码就可以完成工作。

例如,仅用以下单一指令,就可取得所有行程的PID:

ps auxw | awk '{print $2}'
那么,awk是如何处理每一笔记录的呢?

awk对每一条记录,都会套用一个"样式{操作}",如果该行符合样式,就执行指定的操作。样式或操作之一,可以省略。如果只有样式,表示要显示符合样式的数据行;如果只有操作,表示对每一数据行都执行该项操作。

 

语法:

awk"样式"文件:把符合样式的数据行显示出来。

awk '{操作}' 文件:对每一行都执行{}中的操作。

awk '样式{操作}' 文件:对符合样式的数据行,执行{}中的操作。

 

用法

awk的用法1:

awk '/La/' dataf3 
显示含La的数据行。

awk的用法2:

awk '{ print $1, $2 }' dataf3 
显示dataf3每一行的第1和第2个字段。

$1代表第1个字段,$2代表第二字段,其他类推。

awk的用法3:

awk '/La/{ print $1, $2 }' dataf3 
将含有La关键词的数据行的第1及第2个字段显示出来。

awk的用法4:

awk -F: '/^ols3/{ print $3, $4 }' /etc/passwd 
使用选项-F,指定:为分隔字符,账号ols3的uid(第3字段)及gid(第4字段)显示出来。

awk的用法5:

awk -F: 'BEGIN{OFS="+++"}/^ols3/{ print $1,
$2, $3, $4, $5 }' /etc/passwd 
以:为分隔字符,+++为输出字段分隔符,将账号ols3的第1~5栏显示出来。

}执行结果:

ols3+++x+++1002+++1002+++ 
本例中,BEGIN{}区域指示awk一开始先做初始化的操作,即设定OFS="+++"。变量OFS的作用是存储输出字段的分隔符。接着,寻找ols3的账号行,找到后,使用print印出第1 ~ 第5个字段,且彼此用 +++ 隔开。

实例

取得网卡的IP:

ifconfig | grep 'inet addr:' | grep Bcast |
awk '{print $2}' | awk -F: '{print $2}' 
取得网络设备名称:

cat /proc/net/dev | awk -F: '/eth.:|ppp.:|wlan.:/{print $1}' 
在本例中,-F:把分隔字符设为:,而且,采用多选一的样式 /eth.:|ppp.:|wlan.:/。这个样式的意思是:设备名称可以是eth0:、ppp1:、wlan1: 这3个其中之一。一旦找到符合样式的字符串后,去掉:,取其中的第一个域值,因此,可能的答案是eth0或ppp1或wlan1。

 

取得系统内存大小:

cat /proc/meminfo | awk '/MemTotal/{print $2}' 
/proc/meminfo记载主机内存相关数据,其中MemTotal为内存大小,其样本值如下:

MemTotal:       223128 kB

因此,在awk的样式语法中,利用/MemTotal/ 找到这一行,再印出第二个字段,即可得到内存的大小。

 

修改CSV文件各字段的顺序:

以下是数据文件dataf6.csv,想要把第2个字段和第4字段调换:

所在乡镇,学校名称,学校网址,校长姓名,学校电话,VOIP前三码,学校地址

新营市,南新国中,http://www.ns12jh.tnc.edu.tw,ABC,06-656313012,1021,新营市民治路6675号

佳里镇,佳里国中,http://www.jl41jh.tnc.edu.tw,NOP,06-722224432,1146,佳里镇安南路5523号

新营市,新营国小,http://www.sy53es.tnc.edu.tw,DEF,06-632213642,1482,新营市中正路3248号

做法如下:

范例  13-3-1:chcsv24.sh

01.     #! /bin/Bash  
02.  
03.     TMPF='/tmp/tmp.$$' 
04.     cat dataf6.csv | awk -F, 'BEGIN{OFS=","}
{print $1,$4,$3,$2,$5,$6,$7}' > $TMPF  
05.     mv -f $TMPF dataf6.csv 

行3,设定临时文件名。

行4,将数据文件的内容通过管道交给awk处理。awk的字段分隔字符和输出分隔字符,皆设为,。在{}的操作中,调换$2和$4的顺序,再把结果转向存储在临时文件中。

行5,将临时文件覆盖原文件。

 

posted @ 2018-02-28 11:45  小火星_Hirsi  阅读(882)  评论(0编辑  收藏  举报