• linux shell攻略学习笔记二


    1.Cat命令

     

    这么多命令,常用的

    Cat –n file  显示文件以及行数

    Cat -

    echo 'Text through stdin' | cat - file.txt

    Text through stdin

    this is file and test   #这个是file.txt的内容,就是echo打印出管道符接的stdin

    2.录制并回放终端会话

    利用script和scriptreplay命令

    录制
    $ script -t 2> timing.log -a output.session
    type commands;
    …
    ..
    exit

    两个配置文件被当做script命令的参数。其中一个文件(timing.log)用于存储时序信息,

    描述每一个命令在何时运行;另一个文件(output.session)用于存储命令输出。

    -t 选项用于将时序数据导入stderr。

    2> 则用于将stderr重定向到timing.log。

    回放

    利用这两个文件:timing.log(存储时序信息)和output.session(存储命令输出信息),我们

    可以按照下面的方法回放命令执行过程:

    $ scriptreplay timing.log output.session
    # 按播放命令序列输出

    3.Find查找

    1.用正则查找文件

    –name  -iname(忽略大小写)
    find /home/slynux -name "*.txt" –print
    find . -iname "example*" -print
    多个条件查找
    find . ( -name "*.txt" -o -name "*.pdf" ) -print

    按路径匹配

    find /home/users -path "*/slynux/*" -print
    直接用正则
    find . -regex ".*(.py|.sh)$"
    find . -iregex ".*(.py|.sh)$"

    2.否定!

    find . ! -name "*.txt" -print

    3.于目录深度的搜索

    find . -maxdepth 1 -name "f*" –print    #最大深度
    find . -mindepth 2 -name "f*" –print          #最小深度

    4.根据文件类型搜索

    Unix类系统将一切都视为文件。文件具有不同的类型,例如普通文件、目录、字符设备、块
    
    设备、符号链接、硬链接、套接字以及FIFO等。
    
    find . -type d –print  #找目录
    find . -type f –print  #找文件

    5.根据文件时间进行搜索

    这个感觉很少用到 单位是天
    
    访问时间(-atime):用户最近一次访问文件的时间。
    修改时间(-mtime):文件内容最后一次被修改的时间。
    变化时间(-ctime):文件元数据(例如权限或所有权)最后一次改变的时间。
    
    这些整数值通常还带有 - 或 + :- 表示小于,+ 表示大于。

    打印出在最近7天内被访问过的所有文件:

    find . -type f -atime -7 -print

    打印出恰好在7天前被访问过的所有文件:

    find . -type f -atime 7 -print

    以分钟作为计量单位

    -amin(访问时间);
    -mmin(修改时间);
    -cmin(变化时间)。

    打印出访问时间超过7分钟的所有文件:

    find . -type f -amin +7 -print

    find另一个漂亮的特性是 -newer参数。使用 -newer,我们可以指定一个用于比较时间戳 的参考文件,然后找出比参考文件更新的(更近的修改时间)所有文件

    找出比file.txt修改时间更近的所有文件

    find . -type f -newer file.txt -print

    6.基于文件大小的搜索

    find . -type f -size +2k   #大于2KB的文件 小于2k用-  等于不用+-
    除了k之外,还可以用其他文件大小单元。
     b —— 块(512字节)。
     c —— 字节。
     w —— 字(2字节)。
     k —— 1024字节。
     M —— 1024K字节。
     G —— 1024M字节。

    7. 删除匹配的文件

    删除当前目录下所有的 .swp文件:

     $ find . -type f -name "*.swp" -delete

    8. 基于文件权限和所有权的匹配

    find . -type f -perm 644 -print

    # 打印出权限为644的文件

    用途:找出那些没有设置好执行权限的PHP文件

    9. 利用find执行命令或动作(厉害了)

    find命令可以借助选项-exec与其他命名进行结合。

    场景:用 -user找出root拥有的所有文件,然后用-exec更改所有权。

    find . -type f -user root -exec chown slynux {} ;

    在这个命令中,({}其实就是类似查找出的文件的引用)

    {}是一个与 -exec选项搭配使用的特殊字符串。对于每一个匹配的文件,{}会被替换成相应的文件名。例如,find命令找到两个文件test1.txt和test2.txt,其所有者均为slynux,那么find就会执行:chown slynux {}

    它会被解析为chown slynux test1.txt和chown slynux test2.txt。

    ; 通过转义的分号结束

    find . -type f -name "*.c" -exec cat {} ;>all_c_files.txt  #cat文件追加到all_file.txt

    将10天前的 .txt文件复制到OLD目录中

    find . -type f -mtime +10 -name "*.txt" -exec cp {} OLD ;

    -exec结合多个命令

    默认-exec执行的是单个命令,把多个命令写到一个shell脚本中(例如command.sh),然

    后在-exec中使用这个脚本:

    -exec ./commands.sh {} ;

    Print0

    find . -type f -name "*.a" -print
    ./a.a
    ./b.a
    
    find . -type f -name "*.a" -print0
    ./a.a./b.a

    4.xargs

    xargs命令应该紧跟在管道操作符之后,以标准输入作为主要的源数据流。

    command | xargs

    样例文件

    $ cat example.txt # 样例文件
    1 2 3 4 5 6
    7 8 9 10
    11 12
    转单行

    这里默认定界符为$IFS (换行/制表符/空格)

    $ cat example.txt | xargs
    输出:1 2 3 4 5 6 7 8 9 10 11 12
    转多行
    $ cat example.txt | xargs -n 3
    1 2 3
    4 5 6
    7 8 9
    10 11 12
    自定义定界符

    通过参数 –d指定定界符

    $ echo "splitXsplitXsplitXsplit" | xargs -d X
    split split split split

    -d –n可以一起用

    $ echo "splitXsplitXsplitXsplit" | xargs -d X -n 2
    split split
    split split
    一次传多个参数
    --------样例sh脚本
    #!/bin/bash
    #文件名: cecho.sh
    echo $*'#'
    
    --------样例测试文件
    $ cat args.txt
    arg1
    arg2
    arg3

    1.调用三次脚本

    $ cat args.txt | xargs -n 1 ./cecho.sh
    arg1 #
    arg2 #
    arg3 #

    2.三个参数一次传入

    $ cat args.txt | xargs ./cecho.sh
    arg1 arg2 arg3 #

    3.简化重复参数的脚本

    ./cecho.sh -p arg1 -l
    ./cecho.sh -p arg2 -l
    ./cecho.sh -p arg3 -l

    简化后

    $ cat args.txt | xargs -I {} ./cecho.sh -p {} -l
    -p arg1 -l #
    -p arg2 -l #
    -p arg3 -l #

    xargs有一个选项-I,可以提供上面这种形式的命令执行序列。我们可以用-I指定替换字符

    串,这个字符串在xargs扩展时会被替换掉。如果将-I与xargs结合使用,对于每一个参数,命

    令都会被执行一次。

    -I {} 指定了替换字符串

    xargs -0指定null为定界符

    场景:xargs的输入和输出只能是stdin和stdout

    很多文件名中都可能会包含空格符(' '),因此xargs 很可能会误认为它们是定界符(例如,hell text.txt会被xargs误解为hell和text.txt)就必须将 -print0与find结合使用,以字符null ('')来分隔输出。

    用法:

    只要我们把find的输出作为xargs的输入,就必须将 -print0与find结合使用,以字符null ('')也就是xargs -0来分隔输出。

    find . -type f -name "*.a" -print | xargs  wc –l

    优化后:

    find . -type f -name "*.a" -print0 | xargs -0 wc -l

    print0 是将查找结果“扁平化”放到一行,而xargs -0会用空格分割打印出各个文件。

    find ./ -name "*.sh" -print0 |xargs -0
    ./test1.sh  ./test02.sh  ./testlog.sh  ./pass.sh  ./fun.sh

    补充场景:

    一个文件要根据不同参数,运行同一个脚本

    $ cat args.txt
    arg1
    arg2
    arg3

    脚本内容:

    #!/bin/bash
    #文件名: cecho.sh
    echo $*'#'

    普通人调用:

    ./cecho.sh arg1
    ./cecho.sh arg2
    ./cecho.sh arg3

    有了xargs后:

    cat args.txt | xargs -n 1 ./cecho.sh
    arg1 #
    arg2 #
    arg3 #

    还有个厉害的

    $ cat args.txt | xargs -I {} ./cecho.sh -p {} -l
    -p arg1 -l #
    -p arg2 -l #
    -p arg3 -l #

    其中 –p 变量  -l 里-p是不变的,-l也是不变的。

    xargs有一个选项-I,可以提供上面这种形式的命令执行序列。我们可以用-I指定替换字符

    串,这个字符串在xargs扩展时会被替换掉。如果将-I与xargs结合使用,对于每一个参数,命

    令都会被执行一次。

    还可以这样:

    $ cat files.txt | ( while read arg; do cat $arg; done )
    # 等同于cat files.txt | xargs -I {} cat {}

    5.tr 转换

    tr只能通过stdin(标准输入),而无法通过命令行参数来接受输入

    tr [options] set1 set2

    set1和set2代表集合 'A-Z' 和 'a-z'都是集合。

    'ABD-}'、'aA.,'、'a-ce-x'以及'a-c0-9'等均是合法的集合。

    就是替换set1的内容为ste2的内容,set1到set2是严格映射,如hashmap,set1是map的key,set2是map的val。

    echo "HELLO WHO IS THIS" | tr 'A-Z' 'a-z'
    用途1:加解密

    $ echo 12345 | tr '0-9' '9876543210'

    87654 # 已加密

    $ echo 87654 | tr '9876543210' '0-9'

    12345 # 已解密

    用途2:删除字符

    tr有一个选项-d,可以通过指定需要被删除的字符集合,

    $ echo "Hello 123 world 456" | tr -d '0-9'

    Hello world

    # 将stdin中的数字删除并打印出来

    补集-c

    补集就是取反。

    $ echo hello 1 char 2 next 4 | tr -d -c '0-9 '

     1 2 4

    通途3:删除重复

    Tr –s 删除重复  下面是删除重复的空格

    $ echo "GNU is not UNIX. Recursive right ?" | tr -s ' '

    GNU is not UNIX. Recursive right ?

    其他关键字

    比如小写换大写:

    echo "hello word"|tr '[:lower:]' '[:upper:]'

    HELLO WORD

    6.校验和

    用途:Src源有文件盒MD5文件,下载目标下载文件后,用下载的md5校验文件。

    用途2:MD5用来判定2个文件是否是同一个文件。

    Md5

    $ md5sum filename

    68b329da9893e34099c7d8ad5cb9c940 filename

    $ md5sum file1 file2 file3 ..

    当使用多个文件时,输出中会在每行中包含单个文件的校验和:

    [checksum1] file1

    [checksum1] file2

    [checksum1] file3

    校验

    如果需要用所有的.md5信息来检查所有的文件,可以使用:

    $ md5sum -c *.md5

    SAH-1

    Sha-1和MD5类似,注意2点

    1. 命令变为sha1sum
    2. .md5文件变为.sha1。如file_sum.md5改为file_sum.sha1
    加密工具与散列

    感觉没啥用,不写了。

    md5sum和SHA-1已不再安全。因为计算能力 的攀升使其变得容易被破解。推荐使用bcrypt或sha512sum这 类工具进行加密

    8.排序、唯一与重复

    排序

    sort命令既可以从特定的文件,也可以从stdin中获取输入,并将输出写入stdout。uniq 的工作方式和sort一样。

    (2) -n按照数字顺序进行排序:

    $ sort -n file.txt

    (3) -r按照逆序进行排序:

    $ sort -r file.txt

    (4) 按照月份进行排序(依照一月,二月,三月……):

    $ sort -M months.txt

    (5) 合并两个已排序过的文件:

    $ sort -m sorted1 sorted2

    (6) -k指定了排序应该按照哪一个键(key)来进行。

    样例文件

    $ cat data.txt
    1 mac 2000
    2 winxp 4000
    3 bsd 1000
    4 linux 1000

    # 依据第1列,以逆序形式排序

    $ sort -nrk 1 data.txt
    4 linux 1000
    3 bsd 1000
    2 winxp 4000
    1 mac 2000
    # -nr表明按照数字,采用逆序形式排序

    # 依据第2列进行排序

    $ sort -k 2 data.txt
    3 bsd 1000
    4 linux 1000
    1 mac 2000
    2 winxp 4000

    指定多列排序

    $ cat data.txt
    1010hellothis
    2189ababbba
    7464dfddfdfd
    $ sort -nk 2,3 data.txt

    起止位置是2和3,就是group by sort 第二列和第三列;不需要做切割什么的了

    uniq

    uniq只能作用于排过序的数据输入,因此,uniq要么使用管道,要么将排过序的文件作为

    输入,与sort命令结合使用。

    样例文件

    $ cat sorted.txt
    bash
    foss
    hack
    hack

    去重

    $ sort unsorted.txt | uniq

    -u找出不重复,唯一的行。

    $ sort unsorted.txt | uniq -u
    bash
    foss

    -c显示重复次数

    $ sort unsorted.txt | uniq -c
     1 bash
     1 foss
     2 hack

    -d找出重复的行

    $ sort unsorted.txt | uniq -d
    hack

    -s 指定可以跳过前n个字符;

    -w 指定用于比较的最大字符数。

    9.分割文件和

    $ split -b 10k data.file -d -a 4

    -b  除了k(KB)后缀,我们还可以使用M(MB)、G(GB)、c(byte)、w(word)等后缀

    -d 以数字为后缀,可以另外使用-d参数

    -a length可以指定后缀长度

    -l,  --lines=NUMBER      put NUMBER lines per output file按行切割。

    Csplit

    $ cat server.log
    SERVER-1
    [connection] 192.168.0.1 success
    [connection] 192.168.0.2 failed
    [disconnect] 192.168.0.3 pending
    [connection] 192.168.0.4 success
    SERVER-2
    [connection] 192.168.0.1 failed
    [connection] 192.168.0.2 failed
    [disconnect] 192.168.0.3 success
    [connection] 192.168.0.4 failed
    SERVER-3
    [connection] 192.168.0.1 pending
    [connection] 192.168.0.2 pending
    [disconnect] 192.168.0.3 pending
    [connection] 192.168.0.4 failed

    我们需要将这个日志文件分割成server1.log、server2.log和server3.log,这些文件的内容分别

    取自原文件中不同的SERVER部分。那么,可以使用下面的方法来实现:

    $ csplit server.log /SERVER/ -n 2 -s {*} -f server -b "%02d.log" ; rm server00.log
    $ ls
    server01.log server02.log server03.log server.log

    有关这个命令的详细说明如下。

    •  /SERVER/ 用来匹配某一行,分割过程即从此处开始。
    •  /[REGEX]/ 表示文本样式。包括从当前行(第一行)直到(但不包括)包含“SERVER”
    • 的匹配行。
    •  {*} 表示根据匹配重复执行分割,直到文件末尾为止。可以用{整数}的形式来指定分割执
    • 行的次数。
    •  -s 使命令进入静默模式,不打印其他信息。
    •  -n 指定分割后的文件名后缀的数字个数,例如01、02、03等。
    •  -f 指定分割后的文件名前缀(在上面的例子中,server就是前缀)。
    •  -b 指定后缀格式。例如%02d.log,类似于C语言中printf的参数格式。在这里文件名=前缀+后缀=server + %02d.log。

    因为分割后的第一个文件没有任何内容(匹配的单词就位于文件的第一行中),所以我们删

    除了server00.log。

    根据扩展名切分文件名

    借助%操作符可以轻松将名称部分从“名称.扩展名”这种格式中提取出来。你可以按照下面

    的方法从sample.jpg中提取名称。

    file_jpg="sample.jpg"
    name=${file_jpg%.*}
    echo File name is: $name

    输出结果:

    File name is: sample

    下一个任务是将文件名的扩展名部分提取出来,这可以借助 # 操作符实现。

    提取文件名中的 .jpg并存储到变量file_jpg中:

    extension=${file_jpg#*.}
    echo Extension is: jpg
    #输出结果:
    Extension is: jpg

    10.交互输入自动化

    echo –e实现

    样例脚本

    #!/bin/bash
    #文件名: interactive.sh
    read -p "Enter number:" no ;
    read -p "Enter name:" name
    echo You have entered $no, $name;
     
    $ echo -e "1
    hello
    " | ./interactive.sh
    You have entered 1, hello

    我们用echo -e来生成输入序列,-e表明echo会解释转义序列

    Expect实现

    在默认情况下,多数常见的Linux发行版中并不包含expect

    自动化脚本

    #!/usr/bin/expect
    #文件名: automate_expect.sh
    spawn ./interactive.sh
    expect "Enter number:"
    send "1
    "
    expect "Enter name:"
    send "hello
    "
    expect eof

    运行结果如下:

    $ ./automate_expect.sh

    解释脚本:

    Spawn      参数指定需要自动化哪一个命令;

    Expect      参数提供需要等待的消息;

    Send          是要发送的消息;

    expect eof        指明命令交互结束。

    11. &并行进程

    我们利用了Bash的操作符&,它使得shell将命令置于后台并继续执行脚本。这意味着一旦循环结束,脚本就会退出,而md5sum命令仍在后台运行。

    为了避免这种情况,我们使用$!来获得进程的PID,在Bash中,$!保存着最近一个后台进程的PID。我们将这些PID放入数组,然后使用wait命令等待这些进程结束。

  • 相关阅读:
    Autofac(01)
    深入理解ADO.NET Entity Framework(02)
    使用excel 数据透视表画图
    C# 控制CH341进行SPI,I2C读写
    C# winform使用combobox遍历文件夹内所有文件
    通用分页存储过程
    如何让你的SQL运行得更快
    sql优化之使用索引
    SQL优化
    SQL 循环语句几种写法
  • 原文地址:https://www.cnblogs.com/yanghaolie/p/12075464.html
Copyright © 2020-2023  润新知