Chinaunix首页 | 论坛 | 博客
  • 博客访问: 532705
  • 博文数量: 137
  • 博客积分: 3170
  • 博客等级: 中校
  • 技术积分: 1455
  • 用 户 组: 普通用户
  • 注册时间: 2009-03-17 11:47
文章分类

全部博文(137)

文章存档

2015年(2)

2013年(1)

2012年(6)

2011年(5)

2010年(62)

2009年(61)

我的朋友

分类:

2010-07-17 14:30:28

普通的行处理任务用sed很好。
awk最好的部分是它按“列”或“字段”处理的方式和“关联数组”,但awk对正则表达式支持的程度比sed要差些。
以下主要参考于:

9.sed流编辑器
   sed并不与初始化文件打交道,它操作的只是一个拷贝,然后所有的改动如果没有重定向到一个文件,将输出到屏幕。
sed 的編輯指令均由位址(address)與函數(function)兩部份組成 , 其中 , 在執行時 , sed 利用它的位址參數來決定編輯的對象;而用它的函數參數編輯。
9.0 调用sed命令有两种形式:
一般形式:
    sed SCRIPT INPUTFILE...
完整形式:
    sed OPTIONS... [SCRIPT] [INPUTFILE...]
更浅显的形式:
sed [options] 'command' file(s)
sed [options] -f scriptfile file(s)

9.1将oldfile中的day,替换为新文件中的night。
sed ‘s/day/night/’ new
file
sed ‘s/day/night/’ oldfile >newfile
9.2将文件每行末尾添加,
sed s/$/,/ change_config_name.bak
9.3 将行首添加'单引号。
sed "s/^/'/" new
9.4  将行首添加单引号',行尾添加单引号和逗号',。
-e参数使得可以执行多个操作
sed -e "s/^/'/" -e "s/$/',/" new
9.5 sed命令中的定界符/,可以用其他的,不一定为/
9.6  echo "123123123" | sed 's/123/abc/',只替换第一个123为abc,
如果都替换的话,需要加入/g,如下:
echo "123123123" | sed 's/123/abc/g'
9.7  echo "34561" | sed 's/1*/abc/g'
结果为:
abc3abc4abc5abc6abc
有些费解啊!细想想也对,我们用"-"代表什么也没有,那么
-
3-4-5-6-1-字符串的"-"符合1*匹配。
9.8 字符&代表匹配的字符串。
9.9 \1 可以保留部分匹配的结果。
9.10  d命令参数的使用:
 删除含有'/*'
和'--'的行,以下regex并不很严密。

sed -e "/\/\*/d" -e "/--/d" your.sql > your_bak.sql


删除不匹配的行:
sed  '/^\[/ !d' 2010-05-28 > jacky
sed 常用正则表达式:
sed '1,/^$/ d' 以下主要摘自gnu sed manual
关于sed的正则表达式:
(1)对于一些特殊字符("?","+",...),在正则表达式中需要使用"\" ;
(2)  星"*"一般只管它前面的字符。
(3) '
[a-zA-Z0-9]
In the C locale, this matches any
10. awk用法
10.1  前言
10.2 awk概述
可以考虑用awk写程序的某一小部分,实现功能,若有效率问题,再用c改写优化。   数据行    字段   字段分割符FS
10.3如何执行
awk
10.3.1 
$awk 'awk程序' 数据文件文件名
awk程序的主要结构:
Pattern { Actions}
常见之awk 程序其型态如下 :
Pattern1 { Actions1 }

Pattern2 { Actions2 }

......

Pattern3 { Actions3 }
Pattern: "关系表达式"(Relational expression) 

Actions:
由许多awk指令构成. awk的指令与 C 语言中的指令十分类似.   
    awk
会先判断(Evaluate) Pattern 的值, Pattern 判断后的值为true (或不为0的数字,或不是空的字符串), awk将执行该 Pattern 所对应的 Actions.反之, Pattern 之值不为 true, awk将不执行该 Pattern所对应的 Actions.

     Pattern { Actions }
, Pattern 部分被省略,只剩 {Actions}.这种情形表示 "无条件执行这个 Actions".
10.3.2  awk 所内建的字段变量及其涵意如下 :

字段变量

含义

$0

一字符串, 其内容为目前 awk 所读入的数据行.

$1

$0 上第一个字段的数据.

$2

$0 上第二个字段的数据.

...

其余类推

10.3.3awk的内建变量(Built-in Variables)

awk 提供了许多内建变量, 使用者于程序中可使用这些变量来取得相关信息.常见的内建变量有 :

内建变量

含义

NF (Number of Fields)

为一整数, 其值表$0上所存在的字段数目.

NR (Number of Records)

为一整数, 其值表awk已读入的数据行数目.

FILENAME

正在处理的数据文件文件名.

10.3.4 awk的工作流程:
执行awk时, 它会反复进行下列四步骤.
1.自动从指定的数据文件中读取一个数据行.
2.自动更新(Update)相关的内建变量之值. 如 : NF, NR, $0...
3.依次执行程序中 所有 的 Pattern { Actions } 指令.
4.当执行完程序中所有 Pattern { Actions } 时, 若数据文件中还有未读取的数据, 则反复执行步骤1到步骤4.
awk会自动重复进行上述4个步骤, 使用者不须于程序中编写这个循环 (Loop)
10.3.5 awk的数组
10.3.6
重定向(> >>)在awk中使用时,要么都用>> 要么都用>,
如果混合使用,有些版本的awk会出问题。
10.3.7 awk 利用系统资源,与系统交互:
[a. 语法] awk output 指令 | "Shell 接受的命令"
( 如 : print $1,$2 | "sort -k 1" )
[b. 语法] "Shell 接受的命令" | awk input 指令
( 如 : "ls " | getline)
注 : awk input 指令只有 getline 一个.
awk output 指令有 print, printf() 二个.
注意:awk提供另一个调用Shell命令的方法, 即使用awk函数system("shell命令")
例如:
$ awk '
BEGIN{
system("date > date.dat")
getline < "date.dat"
print "Today is ", $2, $3
}
'
但使用 system( "shell 命令" ) 时, awk无法直接将执行中的部分数据输出给Shell 命令. 且 Shell 命令执行的结果也无法直接输入到awk中.

10.3.8 awk程序的执行方式:

若欲执行该awk程序, 来印出文件 today_rpt1 及 today_rpt2 的内容时,
必须于 UNIX 的命令行上执行下列命令 :
方式一 awk -f mydump.awk today_rpt1 today_rpt2
方式二 awk '{print}' today_rpt1 today_rpt2第二种方式系将awk 程序直接写在 Shell 的命令行上, 这种方式仅适合较短的awk程序.
方式三 建立如下之 shell script, 并取名为 mydisplay,
#!/bin/sh
# 注意以下的 awk 与 ' 之间须有空白隔开
awk '
{print}
' $*
# 注意以上的 ' 与 $* 之间须有空白隔开
[ 说 明 : ]
在script文件 mydisplay 中, 指令"awk"与第一个 '  之间须有空格(Shell中并无" awk' "指令).
第一个 ' 用以通知 Shell 其后为awk程序.
第二个 ' 则表示 awk 程序结束.
故awk程序中一律以"括住字符串或字符, 而不使用 ' , 以免Shell混淆.
$* 为 shell script中的用法, 它可用来代表命令行上 "mydisplay之后的所有参数".
例如执行 :
$ mydisplay today_rpt1 today_rpt2
事实上 Shell 已先把该指令转换成 :
awk '
{ print}
' today_rpt1 today_rpt2
本例中, $* 用以代表 "today_rpt1 today_rpt2". 在Shell的语法中, 可用 $1 代表第一个参数, $2 代表第二个参数. 当不确定命令行上的参数个数时, 可使用 $* 表之.
10.3.9 改变 awk 切割字段的方式:
FS = "[ \t:]+" (注: [ \t:]+ 为一Regular Expression )
Regular Expression 中使用中括号 [ ... ] 表示一个字符集合,用以表示任意一个位于两中括号间的字符.故可用"[ \t:]"表示 一个 空白 , tab 或 ":"
Regular Expression中使用 "+" 形容其前方的字符可出现一次

阅读(933) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~