问题集锦(43-45)

    技术2026-08-25  11

    Problem 43. 常用Shell命令集

    Ans

    1.       cut

    将输入行的特定字段裁剪出来,默认情况下cuttab视为字段分隔符。cut不影响输入文件。

    -b list  显示出位于list所指位置的字节。

    -c list  显示出位于list所指位置的字符。

    -d delim 定义字段分隔符为delim字符。

    -f list 显示出list所列出的字段。

    范例

    $ cut –d: -f1 /etc/passwd

    $cut –c 1 /etc/passwd

     

    2.       head

    显示出文件开头的前几行。

    -c n 显示出前n个字节的内容。若n后面附加了km,则计数单位会相应变成千字节(KB)或兆字节(MB)

    -n m 显示出头m行的内容,默认值为10

     

    3.       join

    依据所指定的字段将来自file1file2的两个表格合并成一个表格

    -j1 nfield

    索引字段为file1的第nfield个字段

    -j2 nfield

     索引字段为file2的第nfield个字段

    -j nfield

     file1file2共同的field视为索引字段。

     

    $ join –j 1 file1 file2

     

    4.       od

    以八进制数据格式显示文件内容

    -t type

            a  字符名称

            c  ASCII

            o  八进制

            x  十六进制

    $ od –t a file1

    $od –t c file1

    $od –t x1 file1(每个数值代表一个字节)

    $od –t x2 file1(每个数值代表两个字节)

     

    5.       sort

    读取输入内容,以字母顺序(或其他顺序)输出它们

    -f 不区分大小字母差异。

    -n 以数值顺序排序

    -r 以相反的顺序排序

    -k pos1, [, pos2] 以位于pos1(pos2)的键值为排序依据

    -t sep 改以sep为区别键值的分隔字符(默认值为空格符)

     

    $ ps –aux | sort –k 6 -n

     

    6.       tac

    颠倒输入行的顺序,刚好与cat的效果相反。

     

    7.       tail

    显示出一个或多个文件中的最后几行。

    -c n 显示出文件最后n个字节的内容。若n后面附加了km,则计数单位会相应变成千字节(KB)或兆字节(MB)

    -n m 显示出最后m行的内容,默认值为10

    -f 显示出文件尾端内容后不关闭输入文件,并且在输入文件的末端出现新内容时实时将它们显示出来。常用此项来持续观察日志文件的内容变化情况。

     

    8.       tr string1 string2

    将一个字符串里的字符转译为另一个字符串里相应的字符

    -c 以相反意义解释string1

    -d 丢弃出现于string1中的任何字符

    -s 若输入数据中连续出现string1所含的任一字符,则将连续字符挤压到只剩一个。

     

    $ cat file1 | tr a-z A-Z

    $ cat file1 | tr –s a   消除file1中连续的字符a

    $ cat file1 | tr –d abc 删除file1中所有的字符a, b, c

     

    9.       uniq

    消除连续相同的文本行。通常与sort搭配使用。

           -d 只显示出有重复的行

           -u 只显示出不重复的文本行

           -c 计算重复次数

          

           $ sort file | uniq

           $sort file | uniq -d

    10.   wc

    计算文件内容中的字符数、单词数和行数。

    -c 只显示出字符数

    -l 只显示行数

    -w 只显示出单词数

     

           $ ls | wc -l

     

    11.    xargs [选项] [其他命令] [初始参数]

    将来自stdin的数据逐一作为other_cmd的自变量,逐次执行新的命令直至耗尽stdin为止。如果要执行的新命令有固定的选项或参数,则可以在初始参数列表予以指定。从stdin读入的参数会接在初始参数列表之后。

     

    主要用于解决命令行过长的问题或需要从其他命令的执行结果中中得到所欲执行命令的自变量。

     

    -n maxargs 限制每次传给其他命令的额外自变量的数量。

    -p 交互模式。执行新构成的其他命令之前会提示用户进行确认。

     

    $ ls | xargs rm

    $ find / -type f | xargs –n 1 grep linux

     

    12 find paths expression [action]

        常用搜索条件:

        -name pattern

        -path pattern

        -lname pattern

        找出名称(-name)、路径名称(-path)或符号链接的目标(-lname)匹配pattern模式的文件。pattern可包含shell的文件名通配符(*,? []),路径是相对于搜索起点的。

        -regex regexp

        路径(相对于搜索起点),必须符合regexp正则表达式的描述

        -type f|d|l|b|c|p|s

        只搜索普通文件(f)、目录(d)、符号链接(l)、块设备(b)、字符设备(c)、具名管道设备(p)socket(s)

        -maxdepth N

        -mindepth N

        限制搜索的深度(相对于搜索起点的子目录深度),至少(-mindepth)或最深(-maxdepth)N

        -size N[bckw]

        找出大小为N单位的文件。b, c, k, w分别代表块、单字节字符、千字节()、双字节字组。+N表示大于N-N表示小于N

        -empty

        找出长度为0的普通文件或目录。

        -user username

        -group gpname

        拥有者为username用户或gpname

        -perm mode

        找出访问模式等于mode的文件或目录。使用-mode表示指定位都必须全部设置,而+mode表示任何指定位之一被设置就算符合条件。

        常见的处理动作

        -print

        显示出文件的相对路径(相对于搜索起点)

        -exec cmd /;

        执行指定的shell命令(cmd)。若cmd含有任何shell特殊字符,则它们之前都必须加上/字符,以免shell立即执行它们。在cmd里,可以用”{}”符号(包括双引号在内)来表示find所找出的文件。

        $ find src/ -name “*.c”

        $ find src/ -name “*.c” –exec chmod g+w {} /;

        从根目录开始,找出任何设置了SUID属性文件并产生一份文件列表

        $ find / -type f –perm -4000 –print | tee /tmp/suid_filelist

        找出工作目录下所有的.zip压缩文件并解压缩它们:

        $ find . –name ‘*.zip’ –exec unzip “{}” /;

     

    PS:当查找一个文件名已知的文件,用locate更好。

     

    13 grep

        -c

        只显示匹配模式行的数目,而非匹配模式行本身。

        -h

        同时搜索多个文件时只显示匹配模式和本身,而不加注所属文件。

        -i

        忽略大小写字母的差异。也就是说,模式abc的匹配模式行可以是abc, aBc, Abc, ABC

        -n

    加注匹配模式行于原文件中的行号。若有多个输入文件时,则文件名与行号都会被显示出来。

    -o

    只显示匹配模式的字符串,而不是含有该字符串的整个行。

    -v

    显示出不匹配模式的行

    -E

    以扩展语法来解释regexp, 而不是含有该字符串的整个行。

     

    例子:

    1.  查找含有“linux”或“Linux”字样的行

    $: grep –i linux file1

    $: grep [Ll]inux file1

    $: grep “/<[Ll]inux” file1

     

    2.  取出收信人为(to=)@oreilly.com.tw的所有通信记录:

    $: grep –o “to=.*@oreilly/.com/.tw” /tmp/aug22.log tmp/aug22.oreilly

     

    14 sed

        流过滤工具

        -e cmd

        代表其后的自变量是一道命令。指定多重命令时,每个命令之前都必须以本选项指出。

        -f file

        代表其后的自变量是一个脚本。

        -g

        替换操作的影响范围为“全局”。

     

        编辑命令:

        d

        删除整行文本。

        s

        替换。这是常用的编辑命令,其语法是:

        s/pattern/replacement/[flags]

        flags的值可能为:

        g   全局替换。全文中任何与pattern相匹配的每个文段都会被替换成replacement,而不是只有第一个相匹配者。

        n   替换第n个与pattern相匹配的文段。默认值为1

        p   显示出被成功替换的行。引标记通常会与-n命令行选项并用。

        w file  将完成替换的文本行输出到file文件。

        y   执行类似于tr命令的转换程序。

    例子:

    1.  $: sed ‘3, 5d’ file1  删除文件的第三行到第五行

    2.  $: sed ‘/^#/d’ file1  删除文件中所有以井字号为首的行

    3.  $: sed  y/abc/xyz/ file1 把字母a,b,c换成x,y,z

    4.  $: sed ‘s/^$/@/’ file1 把空行换成@符号

    5.  $: sed ‘s/”/’/g’file1

     

    15. pushd, popd, dirs

        这几个命令可以使得工作目录书签化,就是可以按顺序向前或向后移动工作目录.

    压栈的动作可以保存工作目录列表.选项可以允许对目录栈作不同的操作.

    pushd dir-name 把路径dir-name 压入目录栈,同时修改当前目录到dir-name.

    popd 将目录栈中最上边的目录弹出,同时修改当前目录到弹出来的那个目录.

    dirs 列出所有目录栈的内容($DIRSTACK 便两相比较).一个成功的pushd 或者popd 将会

    自动的调用 dirs 命令.

    下面的命令顺序会说明该命令如何工作:

    [PWD david]$ dirs

    ~

    [PWD david]$ pushd /etc/

    /etc ~

    [PWD etc]$ pushd /var/

    /var /etc ~

    [PWD var]$ pushd /mnt/

    /mnt /var /etc ~

    [PWD mnt]$ pushd /home/

    /home /mnt /var /etc ~

    [PWD home]$ dirs

    /home /mnt /var /etc ~

    [PWD home]$ popd

    /mnt /var /etc ~

    [PWD mnt]$ popd

    /var /etc ~

    [PWD var]$ popd

    /etc ~

    [PWD etc]$ popd

    比较常用的操作是将您的工作目录定义到目录列表中:

    pushd $PWD

     

     

     

    Problem 44 关于函数指针的使用?

    Ans:

     

    Ex1: 形式一

    #include <unistd.h>

    #include <stdio.h>

     

    int max(int a, int b)

    {

        return a > b ? a:b;

    }

     

    typedef int (p)(int, int);

     

    int test(p f, int a, int b)

    {

     

        p* func = f;

        return func(a, b);

    }

     

    int main()

    {

        int a=10;

        int b=9;

        int c;

     

        c = test(max, a, b);

     

        printf("c=%d/n", c);

     

        return 0;

       

    }

     

    Ex2 形式二

    #include <unistd.h>

    #include <stdio.h>

     

    int max(int a, int b)

    {

        return a > b ? a:b;

    }

     

    typedef int (*p)(int, int);

     

    int test(p f, int a, int b)

    {

        p func = f;

        return func(a, b);

    }

     

    int main()

    {

        int a=10;

        int b=9;

        int c;

     

        c = test(max, a, b);

     

        printf("c=%d/n", c);

     

        return 0;

       

    }

     

    Problem 45. Bash Shell简明教程?

    Ans

    1.  常用shell变量

    $#:存储外壳程序中命令行参数的个数。

    $?:存储上一个执行命令的返回值。

    $0:存储外壳程序的程序名。

    $*:是所有位置参数的列表(不包括$0),其形式是单个字符串,串中每个参数由内部域分隔符$IFS分隔。

    $@:存储所有命令行的输入参数,是所有位置参数被分别表示为双引号中的N个字符串,分别表示为($1, $2, …, $n)

    $$:存储外壳程序的PID

    $!:存储上一个后台执行命令的PID

    shell数组:

    定义:

    declare -a SATA_DEVS

    SATA_DEVS=( "sda   8   0   6    644"

                "sdb   8   16  6    644"

                "sdc   8   32  6    644"

                "sdd   8   48  6    644"

                "sde   8   64  6    644"

                "sdf   8   80  6    644"

                )

    访问数组中的元素:

        NUM_ELEMS=${#SATA_DEVS[@]}

        for (( i=0; i<$NUM_ELEMS; i++)); do

            this_entry=${SATA_DEVS[${i}]}

            echo $this_entry

        done

     

    2.  test命令

    1) 整数运算符

    int1 –eq int2

    int1  -ge int2

    int1  -gt int2

    int1  -le int2

    int1  -lt int2

    int1  -ne int2

     

    2) 字符串运算符

    str1 = str2

    str1 != str2

    str              如果str不为空,则返回真

    -n str           如果str长度大于零,则返回真

    -z str           如果str长度等于零,则返回真

     

    3) 文件运算符

    -d filename      是否为目录

    -e filename      文件是否存在

    -f filename      是否为普通文件

    -r filename      是否只读

    -s filename      长度是否大于零

    -w filename      是否可写

    -x filename      是否可执行

    -L filename      是否为软链接文件

    file1 –ot file2 file1旧于file2,则条件成立

        4)逻辑运算符

            !expr                  

            expr1 –o expr2        

            expr1 –a expr2        

    3.  条件表达式

    1) if表达式

    if [ expression ]

    then

         commands

    elif [ expression ]

    then

         commands

    else

         commands

    fi

     

    例子:

    if [ -f .profile ]

    then

         echo “There is a .profile int the current directory.”

    else

         echo “Cound not find the .profile file.”

    fi

     

    2) case 表达式

    case string1 in

    str1)

         commands

         ;;

    str2)

         commands

         ;;

    *)

         commands

    esac

     

    例子:

    case $1 in

    -i)

         count=`grep ^i $2 | wc –l`

         echo “the number of lines in $2 that start with an i is $count”

         ;;

    -e)

         count=`grep ^e $2 | wc –l`

         echo “the number of lines in $2 that start with an e is $count”

         ;;

    *)

         echo “That option is not recogonized”

         ;;

    esac

     

    3) 循环语句

    1.  for 语句

    第一种形式:

    for var int list

    do

         commands

    done

    第二种形式:

    for var (in $@)

    do

         statements

    done

     

    例子:

    for file

    do

         tr a-z A-Z <$file >$file.caps

    done

     

    2.  while语句

    while expression

    do

         statements

    done

     

    例子:

    count=1

    while [ -n “$*” ]

    do

         echo “This is parameter number $count $1”

         shift

         count=`expr $count + 1`

    done

     

    3. until语句

           until expression

            do

                commands

            done

        例子:

        count=1;

        until [ -z “$*” ]

        do

            echo “This is parameter number $count $1”

            shift

            count=`expr $count + 1`

        done

    4) shift 命令

    shift命令用来将存储在位置参数中的当前值左移一个位置

     

    例子:

    while [ “$1” ]

    do

    if [ “$1” = “-i” ]

    then

         infile=”$2”

         shift 2

    elif [ “$1” = “-e” ]

    then

         outfile=”$2”

         shift 2

    else

         echo “Program $0 does not recognize option $1”

    fi

    done

    tr a-z A-Z <$infile >$outfile

     

    4.  函数

    形式:

    fname()

    {

         command

         … …

         command

    }

        调用函数形式:

        fname [param1 param2 param3 …]

    最新回复(0)