天天看点

Shell脚本学习-文件操作和文本处理

Solaris下文件操作和文本处理相关shell整理。

$ls

    -a: all entries; -A: all entries, with the exception of . and ..

    -l: long format; -e:same as -l, 显示时间到秒;  -E: same as -l, 显示时间到纳秒

    -L: 列出symbolic link所指向的实际文件(夹)的属性,但是文件名还是symbolic link的名字,可以和-l一起使用;

    -p: put a slash(/) after each file name if the file is a directory;

    -d: 显示目录本身信息而不是包含的文件的信息; -R 递归到每个子目录

    -t: Sorts by time stamp (latest first); -r: Reverses the order of sort;

    -h: human readable format for file size, xxxK, xxxM, xxxG;

    -v verbose ACL: -l输出再加上详细ACL信息

    -i: 输出inode信息

*默认使用最后修改时间来排序(-t)或者输出列表(-l|-e);

*-u 使用last access time;

*-c 使用i节点文件状态的最后修改时间;

*上述三种时间(access,modification,status change)分别对应st_atime,st_mtime,st_ctime

$touch file, 更新上述三种时间为当前时间;

    -m只更新最后修改时间和状态最后修改时间;

    -a 只更新最后访问时间;

    可以指定一个时间;

         -d YYYY-MM-DDThh:mm:SS[.frac][tz] T为字符T或者空格[,frac]也可;

         -t [[CC]YY]MMDDhhmm[.SS]

$find path-list predicate-list:在指定路径查找.

    例如find .或者find *列出当前目录下的所有文件;find dir列出dir目录下的所有文件。

    -name <pattern>: 查找指定文件。pattern可以包含通配符但是需要加上引号,例如find . -name "aa*"

    -ls,列出查找到文件的属性;,例如find . -name b -ls。

    -exec,执行命令,例如find . -name b -exec rm {} \; ({}代表当前文件路径,用\;分割命令)

    -ok, 同-exec,更安全,执行命令之前要求用户确认

    -type [dfl],指定文件类型,d-directory,f-file,l-link

    -prune,不递归处理子目录,例如 find * -prune -type d 找出当前目录下的所有文件夹

    -o=OR, [-a]=AND可省略,例如find . -name a -o -name b

    ! 对某个表达式取反,例如 find * -prune ! -type d 找出当前目录下的所有不是文件夹的文件

    -size [+-]n[c] 按文件大小查找,+表示大于,-表示小于;c表示字节数,不加c表示block-512字节

    {-ctime|-mtime|-atime} [+-]n n天前状态修改/内容修改/访问过的文件

    -newer timstampfile 比timestampfile修改时间更近的文件

*ls和find命令都可以使用通配符

    ? 匹配任何1个字符  * 匹配任何字符或字符串

    [set] 匹配任何在set中的字符,可指定范围,例如0-9,a-z

    [!set] 匹配任何不在set中的字符

$/usr/bin/grep expression filelist: 在文件内容中查找.-v输出不包括expression的行;-i不分大小写;-n输出行号

    expression为BRE(basic regular expression)基本正则表达式,例如 grep -v "^$" file 过滤空行。

    如果是正则表达式,最好给expression加上引号,例如grep "\\<se" file 查找包含se开头的单词的行。

$/usr/xpg4/bin/grep -E "ab|ad" filelist: -E选项支持ERE(extended regular expression).包含ab或者ad.

    XPG4-X/Open Portability Guide, Fourth Edition; XPG5-即UNIX98或称Single UNIX Specification.

$/usr/bin/egrep 支持ERE.

[:alpha:] 英文字母

[:alnum:] 英文字母和数字

[:digit:] 数字

[:xdigit:]16进制数字

[:blank:] 空格和tab

[:graph:] 非空格字符

[:space:] 空白字符,包括换行

[:cntrl:] 控制字符

[:lower:] 小写

[:upper:] 大写

[:print:] 可显示字符

[:punct:] 标点符号

*以上在正则表达式里面使用时需要放到方括号中.

*[:alpha:]表示匹配字母a,l,p,h,:  表示匹配英文字母的写法是[[:alpha:]]

$file: determine file type,可察看32bit/64bit程序等。

$wc file: 统计文件。-l 行数; -w 字数; -c 字符数。 

$tail -f file: 跟踪文件内容变化。+n, 文件第n行开始的内容; -n, 文件最后n行的内容

$head -n file: 显示头n行的内容。

$cat file: 把文件内容打印到标准输出

    $cat >file: 把标准输入内容写入文件。以ctrl+d结束输入。

    $cat file1 file2 > file3: 把file1和file2的内容合并到file3。

$od [-cx] [file]:octal dump. -x: HEX output; -c: character output.

$fmt file: 格式化文件, -w 指定每行字符宽度,默认为72字符; -s 只分割长行不合并短行,

    例如 sed -n '1,20p' /usr/dict/words | fmt -w 30

$tee file: 拷贝stdout输出到文件. -a 追加到文件末尾.

$dd: 拷贝并转换文件。

   if=输入文件;of=输出文件;bs=n指定block大小;skip=n忽略n输入block;count=n只拷贝n输入block;

   conv=lcase/ucase转换大小写

   例:忽略头1k,拷贝trace.log文件1k内容到conv.log并转换为大写

        dd if=trace.log of=conv.log bs=1024 skip=1 count=1 conv=ucase

$tr string1 string2: 读取stdin,把string1中的每一个字符转换为string2中对应的字符,

    例如 tr abc def < file 把文件中所有字符,a->d,b->e,c->f。

    tr [:lower:] [:upper:] < file 把文件中所有字符从小写转为大写。

    tr -d[c] string1 删除string1。-c complement,取补集,即删除除了string1以外的内容。

    [c-c]指定字符范围;

    [x*n],只可用在string2中,表示n个字符x,如果n省略或者为0,表示n等于string1的长度

    -s 删除连续出现字符为1个;

        例如tr -cs "[a-z]'[A-Z]" "[\n*]" < file,输出文件file中的单词列表,每行一个.

*关于回车(carriage return)换行(line feed),

*Window下用回车换行\r\n(0D0A)来表示,linux下是换行\n(0A)来表示。

*Window上的文件拷到unix上用时,每行后面会多个^M。

*可以用 cat file | tr -d "\r" > newfile 来删除file中的\r。

$sed [-n] [-e script]... [-f scriptfile]... [file]... 流编辑器Stream Editor,

    从文件读入,应用指定编辑命令,结果输出到stdout.

    如果只有1个编辑命令,-e可省略,支持正则表达式,

        例 sed 's/:.*//' /etc/passwd (s命令用来查找替换)删除第一个:后的所有内容.

        例 sed '/[0-9]/d' file, (d命令表示删除)删除包含数字的行;

        例 sed 's/^/#/' file, 给file的所有行前面加上#.

    -n不输出结果,除非在脚本里明确使用p,

        例 sed -n 's/df/DF/gp' file, 只输出被替换过的行(g表示全局替换,否则只替换第一个)

    如果使用一个脚本文件,可以使用特殊的行首,例如使用下面的脚本sed.script,

        sed -e 's/df/DF/g' -f sed.script file, 只输出包含123456的行。

              #n

              /123456/p

    &符号表示匹配表达式的整个文本。例如 sed 's/df/&DF/g' file, 把所有df替换为dfDF.

    可以给匹配表达式加上限定范围,例如 sed '/a[ab]/ s/df/DF/g' file, 在包含aa或者ab的行中替换.

    可以指定一个范围,例如 sed '/^12/,/^45/ s/df/DF/g' file,  从12开头到45开头的行中f替换.

    可以用数字表示行号, $符号表示最后一行, 例如 sed -n '5,$p' file 表示从第5行开始打印到最后一行.

    可以在匹配表达式前加上!表示限定范围以外,

        例如  sed '/a[ab]/ !s/df/&DF/g' file, 在不包含aa或者ab的行中,把所有df替换为dfDF.

    可以使用/以外的界定符,例如 sed 's;/home/export/;/home/export/oracle/;g' file 这里用;作为界定符.

$cmp file1 file2: 比较2个文件,如果相同不输出任何信息,否则输出第一个不同位置到stdout;

    -s 不输出任何信息.如果相同返回值0.

$diff file1 file2: 比较2个文件。- i 忽略大小写; -b 忽略行尾的空格和制表符; -w忽略所有空格和制表符;

$dircmp dir1 dir2: 比较2个目录。-s 不输出相同文件信息; -d 使用diff比较两个目录中都存在的文件内容。

$split -l 1000 file name: 分割文件file,分割后文件每个1000行,前缀name;

    -b 1024, 每个文件1024byte; -b 1024k, 每个文件1024K.

$paste file1 file2: 逐行合并,把第二个文件第一行粘贴到第一个文件第一行后面,依此类推,结果输出到stdout

$cut -d : -f 1,5 /etc/passwd: 选定输出字段;-d 指定分隔符delimiter,默认为tab;

    -f指定字段,-c指定字符, 2者都可以指定多个值(逗号分开),也可以指定范围m-[n],n省略表示到最后

$sort file: 对文件每行进行排序输出到stdout.

    -o outfile 输出到文件;

    -f 忽略大小写; -r 反序; -n 按照数字(numeric)排序

    -m merge files. 文件需要事先排序好。例如sort -mn -o merge.sorted 1.sorted 2.sorted

    -kx 按照第x个字段排序; -t char 以char为字段分隔符,默认为空白字符;

    -b 忽略排序字段开头的空白(和-k配合使用), 例如sort -t: -k3nrb /etc/passwd 按照UID降序

    可以指定多个字段排序,例如 sort -t: -k4nb -k3nb /etc/passwd 先按照GID,再按照UID排序

$uniq [-c|-d|-u] file: 清除排序后文件中的重复记录;

    -c 在记录前显示计数; -d 仅显示重复记录; -u 仅显示未重复记录,

        例如 cut -d: -f4 /etc/passwd | sort -n |uniq -c

$comm file1 file2: select common lines in 2 files.

    两个文件需要事先排序,输出只在文件1存在的行,只在文件2存在的行,2个文件中都存在的行

$join -j1 1 -j2 1 -t : passwd.1 passwd.2: 按照关键字合并2个排好序的文件,

    -j1 -j2分别指定2个文件中关键字段的位置,默认都为1;-t指定输入文件的分隔符,也作为输出的分隔符;

$chmod 777 file: 增加owner, group, other的所有权限(x, w, r; 1->execute; 2->write; 4->read)

    chmod [ugoa]{+|-|=}{rwx} file: u->user; g->group; o->other; a->all;不指定为a。例:chmod go+rw file

    -R递归操作文件夹; -f force mode

$chown -R owner[:group] file...: 改变文件owner,-R递归操作文件夹

$umask [mask]: 显示设置限制新文件权限的掩码; 例如022, g和o的w位不可用, 即u=rwx,g=rx,o=rx

    -S: symbolic output.

$mkdir -p directories: 创建目录,包括不存在的parent directory。

$rm -rf dirname: 删除目录

    -r=Recursively, -f=Removes all files (whether write-protected or not)

$cp source_file target_file/cp source_file target_dir

    cp -r: Recursive, 拷贝目录

    cp -p: Preserve, 保留文件修改时间,ACL等属性。

    cp -P: Preserve(大写P), 保留symbolic links。不加此选项则拷贝link指向的文件。

$mv source_file target_file

    mv source_file target_dir

    mv source_dir target_dir

$ln -s source target: create a symbolic link。注意source要使用全路径。

$tar

    c Create,创建档案文件

    r Replace,添加文件到档案文件末尾

    u Update,更新档案文件中的文件,

        如果不存在或者此文件添加到档案文件后又被更新过,则添加到档案文件末尾。

    t Table of Contents, 列出档案中的内容。

    x Extract, 释放文件。

    f File, 指定tarFile参数。

    v Verbose

        $tar cvf|rvf|uvf tarFile file

        $tar tvf tarFile

        $tar xvf tarFile

$gzip [-v] file: 压缩文件file->file.gz,并删除原始文件file。-v输出压缩比。

    $gzip -cv file 〉xxx.gz: 保留原始文件file并输出压缩结果到stdout。

    $gzip -l xxx.gz: list压缩前后size, 压缩比,原始文件名字。

    $gzip -d xxx.gz: decompress

    $gzip -cdv xxx.gz > file: decompress, 保留原始文件xxx.gz。

*常见脚本起始部分对临时文件的处理:

    先删除其他人的所有权限;产生临时文件名,如果存在环境变量TMPDIR,则用它代替/tmp,

    $$代表进程ID;trap语句在退出时删除临时文件。

        umask 077

        TMPFILE=${TMPDIR-/tmp}/myprog.$$

        trap 'rm -f $TMPFILE' EXIT

    可以用mktemp命令产生临时文件。

        TMPFILE=`mktemp` 如果存在环境变量TMPDIR,在这个目录下生成临时文件。

    可以为mktemp指定一个模板TMPFILE=`mktemp /tmp/myprog.XXXXXX`, XXXXXX部分会被替换。

   指定-d选项生成临时文件夹。

继续阅读