星期三, 三月 01, 2006

[awk] 数据过滤

[root@VmwareHost ~]# ps -ef -aux
Warning: bad syntax, perhaps a bogus '-'? See /usr/share/doc/procps-3.2.3/FAQ
USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND
root 1 0.0 0.2 3308 560 ? S 12:15 0:00 init [3] HOME=/ TERM=linux SELINUX_INIT=
root 2 0.0 0.0 0 0 ? SN 12:15 0:00 [ksoftirqd/0]
root 3 0.0 0.0 0 0 ? S< 12:15 0:00 [events/0]
root 4 0.0 0.0 0 0 ? S< 12:15 0:00 \_ [khelper]
root 5 0.0 0.0 0 0 ? S< 12:15 0:00 \_ [kacpid]
root 18 0.0 0.0 0 0 ? S< 12:15 0:00 \_ [kblockd/0]
root 28 0.0 0.0 0 0 ? S 12:15 0:00 \_ [pdflush]
root 29 0.0 0.0 0 0 ? S 12:15 0:00 \_ [pdflush]
root 31 0.0 0.0 0 0 ? S< 12:15 0:00 \_ [aio/0]
root 19 0.0 0.0 0 0 ? S 12:15 0:00 [khubd]
root 30 0.0 0.0 0 0 ? S 12:15 0:00 [kswapd0]
root 105 0.0 0.0 0 0 ? S 12:15 0:00 [kseriod]
root 180 0.0 0.0 0 0 ? S 12:15 0:00 [kjournald]
root 1018 0.0 0.1 2912 456 ? S<s 12:15 0:00 udevd DEVPATH=/block/fd0 PATH=/sbin:/bin:/usr/sbin:/usr/bin ACTION=ad
root 1284 0.0 0.0 0 0 ? S 12:15 0:00 [kjournald]
root 1893 0.0 0.3 2876 1020 ? Ss 12:15 0:00 /sbin/dhclient -1 -q -cf /etc/dhclient-eth0.conf -lf /var/lib/dhcp/dh
root 1930 0.0 0.2 2844 588 ? Ss 12:15 0:00 syslogd -m 0 SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_VE
root 1934 0.0 0.1 2328 484 ? Ss 12:15 0:00 klogd -x SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_VERSIO
rpc 1962 0.0 0.2 2348 592 ? Ss 12:15 0:00 portmap SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_VERSION
rpcuser 1982 0.0 0.2 2960 756 ? Ss 12:15 0:00 rpc.statd SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_VERSI
root 2010 0.0 0.3 4536 1008 ? Ss 12:15 0:00 rpc.idmapd SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_VERS
root 2087 0.0 0.2 1936 556 ? Ss 12:15 0:00 /usr/sbin/acpid SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT
root 2099 0.0 0.7 9196 2032 ? Ss 12:15 0:00 cupsd SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_VERSION=s
root 2229 0.0 0.6 5204 1652 ? Ss 12:15 0:00 /usr/sbin/sshd SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_
root 2944 0.0 0.8 7660 2228 ? Ss 12:23 0:00 \_ sshd: root@pts/0
root 2946 0.0 0.5 5852 1476 pts/0 Ss 12:23 0:00 \_ -bash USER=root LOGNAME=root HOME=/root PATH=/usr/local/sbin:
root 3012 0.0 0.3 3372 780 pts/0 R+ 12:45 0:00 \_ ps -ef -aux HOSTNAME=VmwareHost.com TERM=vt100 SHELL=/bin
root 2244 0.0 0.3 3260 828 ? Ss 12:15 0:00 xinetd -stayalive -pidfile /var/run/xinetd.pid LC_MONETARY=en_US SELI
root 2254 0.0 0.3 4588 972 ? S 12:15 0:00 /usr/sbin/vsftpd /etc/vsftpd/vsftpd.conf SELINUX_INIT=YES CONSOLE=/de
root 2264 0.0 0.2 2924 552 ? Ss 12:15 0:00 gpm -m /dev/input/mice -t imps2 SELINUX_INIT=YES CONSOLE=/dev/console
htt 2294 0.0 0.1 2580 332 ? Ss 12:15 0:00 /usr/sbin/htt -retryonerror 0 HOSTNAME=VmwareHost.com SHELL=/bin/bash
htt 2295 0.0 1.0 7876 2724 ? S 12:15 0:00 \_ htt_server -nodaemon HOSTNAME=VmwareHost.com SHELL=/bin/bash TERM
root 2305 0.0 0.3 5912 832 ? Ss 12:16 0:00 crond SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_VERSION=s
root 2356 0.0 0.3 2292 1020 ? S<s 12:16 0:00 /sbin/dhclient -1 -q -cf /etc/dhclient-eth0.conf -lf /var/lib/dhcp/dh
xfs 2394 0.0 0.5 4208 1528 ? Ss 12:16 0:00 xfs -droppriv -daemon SELINUX_INIT=YES CONSOLE=/dev/console TERM=linu
root 2404 0.0 0.2 2972 640 ? SNs 12:16 0:00 anacron -s SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_VERS
daemon 2413 0.0 0.2 2604 648 ? Ss 12:16 0:00 /usr/sbin/atd SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_V
dbus 2423 0.0 0.5 13456 1296 ? Ssl 12:16 0:00 dbus-daemon-1 --system SELINUX_INIT=YES CONSOLE=/dev/console TERM=lin
root 2437 0.0 0.4 2940 1044 ? Ss 12:16 0:00 cups-config-daemon SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux I
root 2448 0.1 1.5 6716 4052 ? Ds 12:16 0:02 hald SELINUX_INIT=YES CONSOLE=/dev/console TERM=linux INIT_VERSION=sy
root 2457 0.0 0.4 4528 1204 ? Ss 12:16 0:00 login -- root
root 2888 0.0 0.5 7072 1412 tty1 Ss+ 12:21 0:00 \_ -bash HOME=/root PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/
root 2458 0.0 0.1 3348 408 tty2 Ss+ 12:16 0:00 /sbin/mingetty tty2 HOME=/ TERM=linux SELINUX_INIT=YES PATH=/usr/loca
root 2459 0.0 0.1 1908 408 tty3 Ss+ 12:16 0:00 /sbin/mingetty tty3 HOME=/ TERM=linux SELINUX_INIT=YES PATH=/usr/loca
root 2460 0.0 0.1 1620 408 tty4 Ss+ 12:16 0:00 /sbin/mingetty tty4 HOME=/ TERM=linux SELINUX_INIT=YES PATH=/usr/loca
root 2461 0.0 0.1 1628 408 tty5 Ss+ 12:16 0:00 /sbin/mingetty tty5 HOME=/ TERM=linux SELINUX_INIT=YES PATH=/usr/loca
root 2621 0.0 a.1 2060 408 tty6 Ss+ 12:16 0:00 /sbin/mingetty tty6 HOME=/ TERM=linux SELINUX_INIT=YES PATH=/usr/loca

以前看 AWK 的时候,觉得 BEGIN END  啥的总觉得很复杂,一般看到它们就跳过去了 ,不求甚解 :-),今天用了用,发现也不是那么可怕,就是一层窗户纸嘛 :)

以下是和朋友的聊天(附件是传给我的数据文件):
---------------------------------

(11:52:03)
spritE 微笑面对一切:
老大,awk命令怎样筛选某一列最大值?
(11:53:01) hhdd(FreeBSD now): awk 我不知道,不熟悉,相对来说要复杂点。
(11:53:11) hhdd(FreeBSD now): 如果数据量不大,可以用sort
(11:54:23) hhdd(FreeBSD now): 你给我一些数据我测试下。
(11:55:29) XXXXX@hotmail.com is offering to send file temp.txt
(11:55:42) spritE 微笑面对一切: 第四列最大数
(11:56:51) spritE 微笑面对一切 has closed the conversation window.
(12:01:03) hhdd(FreeBSD now): ft,我用awk做出来了:)
(12:01:09) hhdd(FreeBSD now): awk 'BEGIN{a=0} $4~/[0-9.]/{if($4>a)a=$4} END{print a}' temp.txt
(12:01:09) spritE 微笑面对一切: 怎样怎样
(12:01:41) hhdd(FreeBSD now): $4~/[0-9.] 这个的作用是排除干扰。
(12:01:44) spritE 微笑面对一切: 哇,好复杂
(12:02:21) spritE 微笑面对一切: 9.?那一点有啥用
(12:02:59) hhdd(FreeBSD now): 还行,BEGIN是初始化变量a, 中间是判断并赋值,最后是打印。
(12:04:11) hhdd(FreeBSD now): 你给我的文件前三行是不能进入比较并赋值这个语句中的,所以用这个来排除掉。
(12:04:46) hhdd(FreeBSD now): 就是第四列只能是0-9和点的才能进行比较。
(12:05:24) spritE 微笑面对一切: 厉害厉害
(12:05:24) hhdd(FreeBSD now): awk 'BEGIN{a=0} $4~/^[0-9.]+$/{if($4>a)a=$4} END{print a}' temp.txt
(12:05:43) hhdd(FreeBSD now): 这个会更好一点,加了^和$
(12:06:09) hhdd(FreeBSD now): 表示这一列只能是数字才能参与比较。
(12:06:25) spritE 微笑面对一切: +$有什么作用?
(12:06:41) hhdd(FreeBSD now): 说实话,我以前没有用过BEGIN和END :)
(12:07:03) spritE 微笑面对一切: 用不用好像不影响效果吧
(12:07:15) hhdd(FreeBSD now): +是对[0-9.]起的作用,你可以看看正则表达式。
(12:07:26) hhdd(FreeBSD now): 表示至少要有一个。
(12:08:13) hhdd(FreeBSD now): 在你的这个例子里面是一样的,可是万一某个第四列是 a3 这种样子,你就知道区别了。
(12:11:01) spritE 微笑面对一切: 哦,还真复杂
(12:11:42) hhdd(FreeBSD now): 好好了解一下正则表达式,对你的生活会有帮助的 :)
(12:11:50) spritE 微笑面对一切: 生活?
(12:11:58) spritE 微笑面对一切: 我晕
(12:12:02) hhdd(FreeBSD now): 嗯 :-D
(12:46:15) spritE 微笑面对一切: 老大,我这里看不明白 BEGIN{a=0} $2~/[0-9.]/{if($2>a)a=$2} 能翻译一下么
(12:49:39) hhdd(FreeBSD now): BEGIN{a=0} 这个是在输入 temp.txt之前执行。
(12:51:47) hhdd(FreeBSD now): $2~/[0-9.]/{if($2>a)a=$2} 这个是对输入的每一行进行处理,如果第二列包含 0到9和.,那么比较 第二列的值和a的大小,如果$2大,那么就把$2赋值给a
(12:53:29) hhdd(FreeBSD now): $2~/[0-9.]/{if($2>a){a=$2}} 这样写也许你更好理解?
(12:53:58) spritE 微笑面对一切: {a=$2}这个不明白
(12:54:40) spritE 微笑面对一切: ($2>a)全部都符合这个条件啊
(12:55:32) hhdd(FreeBSD now): -_-! 你又是什么数据?怎么说$2>a都符合?
(12:55:43) hhdd(FreeBSD now): 记得a是变量。
(12:55:47) spritE 微笑面对一切: a=0,
(12:56:20) hhdd(FreeBSD now): a=$2这个是赋值,将$2的值给变量a,现在a的值已经变了。
(12:56:44) hhdd(FreeBSD now): 你有没有了解过编程?
(12:56:49) spritE 微笑面对一切: 有啊
(12:57:18) spritE 微笑面对一切: 但是,全部都大于0啊
(12:57:31) spritE 微笑面对一切: 几乎全部
(12:57:32) spritE 微笑面对一切: root 1018 0.0 0.1 2912 456 ? S<s 12:15 0:00 udevd root 1284 0.0 0.0 0 0 ? S 12:15 0:00 [kjournald] root 1893 0.0 0.3 2876 1020 ? Ss 12:15 0:00 /sbin/dhclient -1 -q -cf /etc/dhclient-eth0.conf -lf /var/lib/dhcp/dh root 1930 0.0 0.2 2844 588 ? Ss 12:15 0:00 syslogd -m 0 root 1934 0.0 0.1 2328 484 ? Ss
(12:57:42) spritE 微笑面对一切: 第四列
(12:57:45) hhdd(FreeBSD now): $2给了a了,a就不再是0了。
(12:57:59) hhdd(FreeBSD now): 而是当前行的$2。
(12:58:46) hhdd(FreeBSD now): BEGIN这个赋值不是对当前行的,而是在行输入之前的赋值,之后就没有用了。
(12:59:12) hhdd(FreeBSD now): 同理,END是在所有的行输入完了之后才启动的。
(12:59:29) hhdd(FreeBSD now): 这样说明白了吗?
(13:02:21) spritE 微笑面对一切: BEGIN{a=0} $2~/[0-9.]/{if($2>a)a=$2} ($2>a)等于N条记录,a=$2那么a就等于多条记录? 哪里有判断最大值?
(13:03:04) hhdd(FreeBSD now): 如果$2比a大,这儿就是判断。
(13:03:38) hhdd(FreeBSD now): 只有$2比a大的时候,才把$2的值给a
(13:03:55) spritE 微笑面对一切: 这里的a还是0吗?
(13:04:51) hhdd(FreeBSD now): 跟你说了,a是变量,在这个例子里面,它永远取比自己大的值。
(13:05:36) spritE 微笑面对一切: 这个a变量是awk内置变量还是你自己定的?
(13:05:47) hhdd(FreeBSD now): awk '$4~/^[0-9.]+$/{if($4>a){a=$4;process=$11}} END{printf("%s: %.1f\n",process,a)}' temp.txt
(13:05:58) hhdd(FreeBSD now): 好了,甩开BEGIN先。
(13:06:07) hhdd(FreeBSD now): a是我定义的。
(13:07:56) hhdd(FreeBSD now): 可能是 BEGIN 和 END 在这儿让你迷惑了。
(13:08:10) spritE 微笑面对一切: 不是,是那个a
(13:08:37) spritE 微笑面对一切: 在哪里定义它为取最大值?
(13:11:05) spritE 微笑面对一切: "a=$4"跟"$4=a"不一样?
(13:13:05) hhdd(FreeBSD now): 嗯, 有十个(或更多)房间,每个里面放了一个苹果,不知道那个最大,现在你提个篮子(a),按顺序走进房间,刚开始,篮子是空的,所以,把第一个房间的苹果放 到篮子里,接着往下走,如果这个房间里面的苹果比你篮子里面的大,就把这个房间的苹果放到篮子里,并把以前的扔掉,这样,你走完所有的房间之后,你篮子里 的苹果是不是最大的?
(13:14:13) hhdd(FreeBSD now): 在上面的例子里,篮子就是 a , $4就是每个房间的苹果。
(13:15:50) spritE 微笑面对一切: 那就是有多少个房间,就要对比多少次?
(13:16:04) hhdd(FreeBSD now): 是啊。
(13:16:41) spritE 微笑面对一切: {if($4>a){a=$4} 这样是1次,把最大那个苹果放进篮子中
(13:16:57) hhdd(FreeBSD now): 嗯 :-D
(13:17:35) spritE 微笑面对一切: 如果房间很多很多,那么这个脚本运行岂不是很费资源?
(13:18:25) hhdd(FreeBSD now): 看有多少,awk的效率非常高的。
(13:18:45) hhdd(FreeBSD now): 几万行对它来说就是小意思。
(13:19:04) spritE 微笑面对一切: {if($4>a){a=$4}它自动会循环?不用我们指定?
(13:19:35) hhdd(FreeBSD now): awk是基于行的处理,一行一行的。
(13:19:51) spritE 微笑面对一切: 哦,明白了
(13:20:09) spritE 微笑面对一切: 苹果(A)
(13:20:51) hhdd(FreeBSD now): 奇怪,为什么我会用苹果而不是桔子呢?
(13:21:28) hhdd(FreeBSD now): 有可能是小时候,教科书都是用苹果吧。
(13:23:10) spritE 微笑面对一切: 差点吓死我
(13:24:50) spritE 微笑面对一切: 还有{}里面是放什么的?动作,赋值?还有什么
(13:25:04) spritE 微笑面对一切: ()里面就是放条件的
(13:26:20) hhdd(FreeBSD now): 一系列的语句。

0 Comments:

发表评论

<< Home