zoukankan      html  css  js  c++  java
  • linux(5)--补充(管道| / 重定向> / xargs)/find 与xargs结合使用/vi,grep,sed,awk(支持正则表达式的工具程序)

    本节中正则表达式的工具程序 grep,sed和awk是重点,也是难点!!!

    先补充一下
    一. 管道| / 重定向> / xargs
    如:
    1. 管道和重定向的区别:具体可以见 http://www.cnblogs.com/chengmo/archive/2010/10/21/1856577.html
    以此为例: cat test.sh test1.sh 2>/dev/null | grep -n 'echo' 
    此时若test.sh 不存在,报错信息不会输出到屏幕中,而是转入 /dev/null中,如果不存在标准错误重定向 2>,则错误信息会显示到屏幕中,重定向主要用于对标准输入输出的处理,控制输出的路径是屏幕还是写入到标准文件中,
    管道主要是用于接收输入的内容并进行操作处理。而且作用接收标准输入的命令才可以用作管道右边。否则传递过程中数据会抛弃。 常用来作为接收数据管道命令有:sed,awk,cut,head,top,less,more,wc,join,sort,split 等等,都是些文本处理命令

    2. xargs是产生某个命令的参数,即把 | 读入的stdin的内容作为参数,传递给后面的命令
    为什么要有xargs?
    xargs了:
    正常情况下,linux中的很多命令和工具,比如grep和awk,是可以通过管道,获得内容,当做输入参数的
    但是对于cp,echo等命令,不识别从(终端中的)标准输入所获得的内容,而识别,命令后面的内容的,当做参数。
    且Linux 2.6.23之前,任意长(足够长,太长)的参数命令,是无法输入到命令中的
    所以,才有了xargs:将(足够长的,太长的)输入,分割成一个参数子列表,子列表中的参数,长度就很短,就可以被接受了。
    常用格式:
    | xargs -参数 ( 文件) 命令
    (1)-0 :当sdtin含有特殊字元时候,将其当成一般字符,像/'空格等
    $ echo "/ /  "|xargs -0 echo
    / /  
    (2)-a file 从文件中读入作为sdtin
    $ xargs -a 1.txt echo
    yuanyuan
    (3)-e flag ,注意有的时候可能会是-E,flag必须是一个以空格分隔的标志,当xargs分析到含有flag这个标志的时候就停止。
    $ cat 1.txt |xargs -E 'ddd' echo
    aaa bbb ccc
    (4)-n num 后面加次数,表示命令在执行的时候一次用的argument的个数,默认是用所有的。
    $ cat 1.txt |xargs -n 2 echo
    aaa bbb
    ccc ddd
    a b
    (5)-p 操作具有可交互性,每次执行comand都交互式提示用户选择,当每次执行一个argument的时候询问一次用户
    $ cat 1.txt |xargs -p echo
    echo aaa bbb ccc ddd a b ?...y
    aaa bbb ccc ddd a b
    $ cat 1.txt |xargs -p echo
    echo aaa bbb ccc ddd a b ?...n
    (6)-t 表示先打印命令,然后再执行。
    $ cat 1.txt |xargs -t echo
    echo aaa bbb ccc ddd a b 
    aaa bbb ccc ddd a b
    (7)-i 或者是-I,这得看linux支持了,将xargs的每项名称,一般是一行一行赋值给{},可以用{}代替,注意,-I 必须指定替换字符 -i 是否指定替换字符-可选
    [yuanyuan@localhost Desktop]$ ls *.txt |xargs -t -i mv {} {}.bak
    mv c.txt c.txt.bak
    mv don.txt don.txt.bak
    (8)-r  no-run-if-empty 如果没有要处理的参数传递给xargsxargs 默认是带 空参数运行一次,如果你希望无参数时,停止 xargs,直接退出,使用 -r 选项即可,其可以防止xargs 后面命令带空参数运行报错。
    $ echo ""|xargs -t mv
    mv 
    mv: missing file operand
    Try `mv --help' for more information.
    (9)-d delim 分隔符,默认的xargs分隔符是回车,argument的分隔符是空格,这里修改的是xargs的分隔符
    $ cat 1.txt.bak 
    aaa@ bbb ccc@ ddd
    a b
    $ cat 1.txt.bak |xargs  -d '@' echo
    aaa  bbb ccc  ddd
    a b

    find与xrags
    $find . -name "install.log" -print | cat
    ./install.log                                                 #显示从管道传来的内容,仅仅作为字符串来处理
    $find . -name "install.log" -print | xargs cat
    aaaaaa                                                      #将管道传来的内容作为文件,交给cat执行。也就是说,该命令执行的是如果存在install.log,那么就打印出这个文件的内容。
    1、在当前目录下查找所有用户具有读、写和执行权限的文件,并收回相应的写权限:
    # find . -perm -7 -print | xargs chmod o-w
    2、查找系统中的每一个普通文件,然后使用xargs命令来测试它们分别属于哪类文件
    # find . -type f -print | xargs file
    ./liyao: empty
    3、尝试用rm 删除太多的文件,你可能得到一个错误信息:/bin/rm Argument list too long. 用xargs 去避免这个问题
    $find ~ -name ‘*.log’ -print0 | xargs -i -0 rm -f {}
    4、查找所有的jpg 文件,并且压缩它
    # find / -name *.jpg -type f -print | xargs tar -cvzf images.tar.gz
    5、拷贝所有的图片文件到一个外部的硬盘驱动 
    # ls *.jpg | xargs -n1 -i cp {} /external-hard-drive/directory


    二. 正则表达式
    用特殊字符的排列用来搜索/删除/替换一行或多行字符,支持正则表达式的工具程序,vi,grep,sed,awk
    正则表达式常用在邮件服务器中用于删除垃圾邮件。


    1.grep(查找有相关字符串的,显示该行)
    grep全称是Global Regular Expression Print,表示全局正则表达式版本,它的使用权限是所有用户
    grep [cinvs] '搜索的字符串 ' filename
    (1)主要参数
    -a :二进制文本中,以文本文件的方式搜索结果
    -c:只输出匹配行的计数。
    -i:不区分大小写(只适用于单字符)。
    -n:显示匹配行及行号。
    -s:不显示不存在或无匹配文本的错误信息。
    -v:反向选择,显示不包含匹配文本的所有行。
    (2)搜索的字符串常用的正则表达式:
      :转义字符,忽略正则表达式中特殊字符的原有含义。
    ^ :匹配以某个字符串开始的行。
    $ : 匹配以某个字符串结束的行。
    <:从匹配正则表达式的行开始。
    >:到匹配正则表达式的行结束。
    [ ]:在[]内个某单个字符,如[A]即A符合要求 。
    [ - ] :属于[ - ]所标记的范围字符,如[A-Z],即A、B、C一直到Z都符合要求 。
    .  :表示一定有1个任意字符。
    * :重复前面0个或多个字符。
    例:
    (1)[yuanyuan@localhost Desktop]$ grep "find" sw //显示有find的行
    find: `yxy': No such file or directory
    [yuanyuan@localhost Desktop]$ grep -v "find" sw //不显示有find的行
    ./yy/y
    [yuanyuan@localhost Desktop]$ grep -in 'find' sw //显示行号不区分大小写
    2:find: `yxy': No such file or directory
    3:FIND YOU
    如何更改文件的语系?
    LANG=en
    export LANG
    (2)用[ ]代表集合字符(只是其中一个)
    如:
    [yuanyuan@localhost Desktop]$ grep -n [^7]huhu sw //^在[ ]内代表反向选择,在[ ]外代表以..开头,如[^a-z]即不是字母
    7:huhuhuhuhu1huhu
    [yuanyuan@localhost Desktop]$ grep -n [1-6]huhu sw //[ ]代表范围在1-6的某一个数字。[0-9][a-z][A-Z],或[a-zA-Z0-9]
    7:huhuhuhuhu1huhu
    (3)行首与行尾字符(^与$)
    如:
    [yuanyuan@localhost Desktop]$ grep -v '^$' sw | grep -v '^#' //去掉空白行,且不以#开头的
    ./yy/y
    find: `yxy': No such file or directory
    FIND YOU
    fww1
    f8fj8
    huhu7huhu
    huhuhuhuhu1huhu

    [yuanyuan@localhost Desktop]$ grep -n '.$' sw //以.结尾的,注意!!这里因为.有特殊含义,所以用转义字符
    5:f8fj8.
    7:huhuhuhuhu1huhu.
    (4)任意一个字符. 与 重复字符* ,
    如:[yuanyuan@localhost Desktop]$ grep -n 'h.h' sw //一个.代表一个字符
    6:huhu7huhu
    7:huhuhuhuhu1huhu.
    *代表重复0个或多个前面的re字符,如g*g,g*代表空字符或一个以上的g
    (5)连续n个{ },注意用转义字符
    [yuanyuan@localhost Desktop]$ grep -n 'w{2}' sw
    4:fww1


    2.sed (和akw一样,都是行编辑器,逐行对数据进行处理)
    sed 是一种在线编辑器(,它一次处理一行内容。处理时,把当前处理的行存储在临时缓冲区中,称为“模式空间”(pattern space),接着用sed命令处理缓冲区中的内容,处理完成后,把缓冲区的内容送往屏幕。接着处理下一行,这样不断重复,直到文件末尾。文件内容并没有 改变,除非你使用重定向存储输出。
    它的强大之处在于可以以行的方式来脚本化处理文本.它的主要功能就是删,查,换和添加.
    命令格式:
    (1)sed [options] 'command' file(s)  
    (2)sed [options] -f scrīptfile file(s) 
    options:
    -e command, --expression=command 允许多台编辑。
    -h, --help 打印帮助,并显示bug列表的地址。
    -n, --quiet, --silent 取消默认输出。
    -f, --filer=scrīpt-file 引导sed脚本文件名。
    -V, --version 打印版本和版权信息。

    command:(常用的)
    a/ 在当前行后面加入一行文本。
    b lable 分支到脚本中带有标记的地方,如果分支不存在则分支到脚本的末尾。 
    c/ 用新的文本改变本行的文本。 
    d 从模板块(Pattern space)位置删除行。 
    D 删除模板块的第一行。 
    i/ 在当前行上面插入文本。 
    h 拷贝模板块的内容到内存中的缓冲区。 
    H 追加模板块的内容到内存中的缓冲区。
    g 获得内存缓冲区的内容,并替代当前模板块中的文本。 
    G 获得内存缓冲区的内容,并追加到当前模板块文本的后面。
      
    元字符集 
    ^ 锚定行的开始 如:/^sed/匹配所有以sed开头的行。 
    $ 锚定行的结束 如:/sed$/匹配所有以sed结尾的行。 
    . 匹配一个非换行符的字符 如:/s.d/匹配s后接一个任意字符,然后是d。
    * 匹配零或多个字符 如:/*sed/匹配所有模板是一个或多个空格后紧跟sed的行。 
    [] 匹配一个指定范围内的字符,如/[Ss]ed/匹配sed和Sed。 
    [^] 匹配一个不在指定范围内的字符,如:/[^A-RT-Z]ed/匹配不包含A-R和T-Z的一个字母开头,紧跟ed的行。 
    /(../) 保存匹配的字符,如s//(love/)able//1rs,loveable被替换成lovers。 
    & 保存搜索字符用来替换其他字符,如s/love/**&**/,love这成**love**。 
    /< 锚定单词的开始,如://<love/匹配包含以love开头的单词的行。 
    /> 锚定单词的结束,如/love/>/匹配包含以love结尾的单词的行。 x/{m/} 重复字符x,m次,如:/0/{5/}/匹配包含5个o的行。 
    x/{m,/} 重复字符x,至少m次,如:/o/{5,/}/匹配至少有5个o的行。 x/{m,n/} 重复字符x,至少m次,不多于n次,如:/o/{5,10/}/匹配5--10个o的行。 

    实例 
    2.1删除:d命令
           *    $ sed '2d' example-----删除example文件的第二行。
           *    $ sed '2,$d' example-----删除example文件的第二行到末尾所有行。
           *    $ sed '$d' example-----删除example文件的最后一行。
           *    $ sed '/test/'d example-----删除example文件所有包含test的行。
    2.2替换:s命令
           *    $ sed 's/test/mytest/g' example-----在整行范围内把test替换为mytest。如果没有g标记,则只有每行第一个匹配的test被替换成mytest。
           *    $ sed -n 's/^test/mytest/p' example-----(-n)选项和p标志一起使用表示只打印那些发生替换的行。也就是说,如果某一行开头的test被替换成mytest,就打印它。
           *    $ sed 's/^192.168.0.1/&localhost/' example-----&符号表示替换换字符串中被找到的部份。所有以192.168.0.1开头的行都会被替换成它自已加 localhost,变成192.168.0.1localhost。
           *    $ sed -n 's//(love/)able//1rs/p' example-----love被标记为1,所有loveable会被替换成lovers,而且替换的行会被打印出来。
           *    $ sed 's#10#100#g' example-----不论什么字符,紧跟着s命令的都被认为是新的分隔符,所以,“#”在这里是分隔符,代替了默认的“/”分隔符。表示把所有10替换成100。
    2.3选定行的范围:逗号
           *    $ sed -n '/test/,/check/p' example-----所有在模板test和check所确定的范围内的行都被打印。
           *    $ sed -n '5,/^test/p' example-----打印从第五行开始到第一个包含以test开始的行之间的所有行。
           *    $ sed '/test/,/check/s/$/sed test/' example-----对于模板test和west之间的行,每行的末尾用字符串sed test替换。
    2.4多点编辑:e命令 
           *    $ sed -e '1,5d' -e 's/test/check/' example-----(-e)选项允许在同一行里执行多条命令。如例子所示,第一条命令删除1至5行,第二条命令用check替换test。命令的执 行顺序对结果有影响。如果两个命令都是替换命令,那么第一个替换命令将影响第二个替换命令的结果。
           *    $ sed --expression='s/test/check/' --expression='/love/d' example-----一个比-e更好的命令是--expression。它能给sed表达式赋值。
    2.5从文件读入:r命令 
           *    $ sed '/test/r file' example-----file里的内容被读进来,显示在与test匹配的行后面,如果匹配多行,则file的内容将显示在所有匹配行的下面。
    2.6写入文件:w命令
           *    $ sed -n '/test/w file' example-----在example中所有包含test的行都被写入file里。
    2.7追加命令:a命令
           *    $ sed '/^test/a//--->this is a example' example<-----'this is a example'被追加到以test开头的行后面,sed要求命令a后面有一个反斜杠。
    2.8插入:i命令
       $ sed '/test/i//
       new line
       -------------------------' example
       如果test被匹配,则把反斜杠后面的文本插入到匹配行的前面。
    下一个:n命令
           *    $ sed '/test/{ n; s/aa/bb/; }' example-----如果test被匹配,则移动到匹配行的下一行,替换这一行的aa,变为bb,并打印该行,然后继续。
    2.9变形:y命令 
           *    $ sed '1,10y/abcde/ABCDE/' example-----把1--10行内所有abcde转变为大写,注意,正则表达式元字符不能使用这个命令。
    2.10退出:q命令 
           *    $ sed '10q' example-----打印完第10行后,退出sed。
    2.11保持和获取:h命令和G命令 
           *    $ sed -e '/test/h' -e '$G example-----在sed处理文件的时候,每一行都被保存在一个叫模式空间的临时缓冲区中,除非行被删除或者输出被取消,否则所有被处理的行都将 打印在屏幕上。接着模式空间被清空,并存入新的一行等待处理。在这个例子里,匹配test的行被找到后,将存入模式空间,h命令将其复制并存入一个称为保 持缓存区的特殊缓冲区内。第二条语句的意思是,当到达最后一行后,G命令取出保持缓冲区的行,然后把它放回模式空间中,且追加到现在已经存在于模式空间中 的行的末尾。在这个例子中就是追加到最后一行。简单来说,任何包含test的行都被复制并追加到该文件的末尾。
    2.12保持和互换:h命令和x命令 
           *    $ sed -e '/test/h' -e '/check/x' example -----互换模式空间和保持缓冲区的内容。也就是把包含test与check的行互换。
    脚本 
    Sed脚本是一个sed的命令清单,启动Sed时以-f选项引导脚本文件名。Sed对于脚本中输入的命令非常挑剔,在命令的末尾不能有任何空白或文本,如果在一行中有多个命令,要用分号分隔。以#开头的行为注释行,且不能跨行。
       *    在sed的命令行中引用shell变量时要使用双引号,而不是通常所用的单引号。下面是一个根据name变量的内容来删除named.conf文件中zone段的脚本:
         name='zone/ "localhost"'
         sed "/$name/,/};/d" named.conf

    [yuanyuan@localhost Desktop]$ cat don.txt |sed -e '4d' -e '6c woxiangya' >haha //删除第4行,将前6行复制到haha中,
    sed有两个以上的参数时需要用-e ,注意,源文件一直不变,变的是haha

    3.awk(主要用于域的作用)
    命令行方式
    awk '{pattern + action}' {filenames}
    awk [-F field-separator] 'commands' input-file(s)

    其中,commands 是真正awk命令,[-F域分隔符]是可选的。 input-file(s) 是待处理的文件。
    在awk中,文件的每一行中,由域分隔符分开的每一项称为一个域。通常,在不指名-F域分隔符的情况下,默认的域分隔符是空格。

    (1)[yuanyuan@localhost Desktop]$ last -n 5 |awk '{print $1}'
    yuanyuan
    yuanyuan
    yuanyuan
    reboot
    yuanyuan
    (2)[yuanyuan@localhost Desktop]$ last -n 5 |awk '{print $1 " " $3}' //第一域和第三域,中间以tab键隔开
    yuanyuan :0.0
    yuanyuan :0.0
    yuanyuan :0
    reboot boot
    yuanyuan :0.0

    wtmp Mon
    (3)[yuanyuan@localhost Desktop]$ last -n 5 |awk '{print $1 " lines:" NR $3 " colums:" NF }' //NR显示行号,NF显示有多少个字符
    yuanyuan lines:1:0.0 colums:10
    yuanyuan lines:2:0.0 colums:10
    yuanyuan lines:3:0 colums:10
    reboot lines:4boot colums:11
    yuanyuan lines:5:0.0 colums:10
    lines:6 colums:0
    wtmp lines:7Mon colums:7
    (4)[yuanyuan@localhost Desktop]$ cat /etc/passwd | awk 'BEGIN{":"} $3>10 {print $1 " " $3 }' //用BEGIN来显示变量的要求
    第三列大于10的所有的第一列与第三列

    更详细的可以见:http://www.cnblogs.com/ggjucheng/archive/2013/01/13/2858470.html

    4.比较两个文件

    (1)diff: 以行为单位比较
    diff -s file 1 file 2 结果显示
    [yuanyuan@localhost Desktop]$ diff -s don.txt haha
    5,6c5 //5,6行被替换成右边的
    < yuan
    < do
    ---
    > woxiangya
    (2)cmp: 以位为单位比较,主要用于二进制文件比较
    cmp -s file 1 file 2
    (3)patch (补丁文件,用diff比较后生成补丁文件)
    diff 旧文件/新文件 > diff.patch

  • 相关阅读:
    简单的模板解析函数
    HTML通过事件传递参数到js 二 event
    HTML通过事件传递参数到js一
    通过this获取当前点击选项相关数据
    LeetCode 20. 有效的括号(Valid Parentheses)
    LeetCode 459. 重复的子字符串(Repeated Substring Pattern)
    LeetCode 14. 最长公共前缀(Longest Common Prefix)
    LeetCode 168. Excel表列名称(Excel Sheet Column Title)
    LeetCode 171. Excel表列序号(Excel Sheet Column Number) 22
    LeetCode 665. 非递减数列(Non-decreasing Array)
  • 原文地址:https://www.cnblogs.com/alwayswyy/p/5191137.html
Copyright © 2011-2022 走看看