https://blog.csdn.net/rabo123/article/details/83590245#3.until
先上一道编程作业:
- 实现一个Shell脚本,可以在指定的目录下查找某个文件/目录.
- 如果找到该文件/目录,显示其完整路径名
- 如果找到多个文件/目录,则每个文件名都显示
- 如果找不到,则输出例如“文件找不到”等的提示
命令格式如下:
SCRIPT_NAME SEARCH_ON_DIR SEARCH_FILENAME




#! /bin/bash#path=`cd $(dirname $0);pwd -P`#echo the current path (shellfile) is:$path#从指定目录下找出所有要查询的文件并输出文件位置echo start time=`date`echo -e# 递归查找function func{local num=0for file in `ls $2`doif [ -L $2"/""$file" ]thencontinueelseif [ -d $2"/""$file" ]thenpath=$2"/""$file"func $1 $pathlet num=$num+$?elseif [ $1 = $file ]thenlet num=$num+1echo file pwd= $2"/""$file"fififidonereturn $num}#func $2 "$path""/"$1 #此命令可查找当前目录的子目录,即调用shell时传相对路径func $2 $1# $2代表待查找的文件,$1代表哪个目录下开始查找fnum=$?if [ $fnum = 0 ]thenecho "文件找不到"elseecho -e "\nsuccessfully find $fnum files"fiecho -eecho end time=`date`
一、变量
hell编程中分为两种变量,第一种是我们自己定义的变量(自定义变量),第二种是Linux已定义的环境变量(环境变量, 例如:$PATH, $HOME 等…, 这类变量我们可以直接使用)。
#!/bin/bash#使用环境变量echo $PATH#自定义变量hellohello="hello world"echo $hello#在第5行中,我们在自定义变量时,使用了双引号。#在shell编程中, 如果变量出现空格或者引号,那么也必须加引号, 否则就可以省略。#还有一点需要注意,定义变量的时候,“=”左右千万不要有空格啊。
将linux命令执行结果赋值给变量
#!/bin/bash# 两种方式来将Linux命令执行结果保存到变量path=$(pwd)files=`ls -al`echo current path: $pathecho files: $files
注意:
变量的赋值 ver2=$ver1 等号左右没有空格,变量的比较 ver2 = ver1 等号左右都要有空格,
且条件判断 [ condition ]中 condition 与左右括号间都要有空格
1.变量赋值:
name=lbg 等号前后不能有空格<br /> name="Lebron James" 变量值中有空格要用双引号<br /> echo ${name} 用${}更保险<br /> shopt -s -o nounset 设置“先声明再使用”<br />
2.取消变量:
unset 释放变量和函数的内存<br />
3.位置参数:
${n}:输入的第n个参数($0表示脚本名字)<br /> $#:输入参数的数量<br /> $@:输入的所有参数<br /> $!:输入的最后一个参数<br /> $?:上一个命令的返回值(用于在脚本中判断之前命令的执行状态,任何非0的返回都表示非正常执行)<br />
4.数组:
declare -a Array=('ladawn' 'lbg' 'lbj')<br />
5.只读变量:
declare -r N=10<br /> readonly N=10<br />
6.函数中的变量:
若不声明local,则函数中的变量也为全局变量。<br /> 若声明为local(local var=200),则变量的作用域只在函数内。<br />
7.引用:
双引号:弱引用,特殊符号($、\、`)仍然解析为特殊的意义。<br /> 单引号:强引用,所有的字符都是字面意思,不再有特殊意义。<br />
8.命令替换:
A=$(data)或者A=`data`,表示将data命令的输出结果取出,赋给A<br />
9.bc运算:
用于浮点数计算输出。通过管道使用。<br /> tatal=$(echo "34/15" | bc)<br />
9.数值运算:
let "sum+=1" 表示sum = sum+1<br /> let "j=sum%2" 表示j = sum % 2 <br />[https://www.cnblogs.com/surpassme/p/9944091.html](https://www.cnblogs.com/surpassme/p/9944091.html)
二、条件判断
2.bash中的条件判断
条件测试类型:
整数测试,字符测试,文件测试
条件测试的表达式:
[ express ]:注意括号两侧有空格,括号中的表达式是关键字
怎么写一个条件表达式:
整数比较:
-eq:测试两个整数是否相等,$A -eq $B
-ne:测试两个整数是否不等,不等为真,相等为假
-gt:测试一个数是否大于一个数,大于为真,小于为假
-lt:测试一个数是否小于一个数,小于为真,大于为假
-ge:大于或等于
-le:小于或等于
文件测试:
-e 文件名/文件路径 测试文件是否存在
-f 文件名/文件路径 测试文件是否为普通文件
-d 文件名/文件路径 测试文件是否是目录
-r 文件名/文件路径 测试文件是否是可读的
-w 文件名/文件路径 测试文件是否是可写的
-x 文件名/文件路径 测试当前用户是否可读可写可执行
三、函数
Shell 函数定义的语法格式如下:
# 代码格式function funcname(){commands}
和其它编程语言不同的是,Shell 函数在定义时不能指明参数,但是在调用时却可以传递参数,并且给它传递什么参数它就接收什么参数。
Shell 也不限制定义和调用的顺序,你可以将定义放在调用的前面,也可以反过来,将定义放在调用的后面。
eg:
!/bin/bashfunction getsum(){local sum=0for n in $@do((sum+=n))donereturn $sum}getsum 10 20 55 15 #调用函数并传递参数echo $?
四、神奇的Bash文件名处理命令
dirname 和 basename
basename命令用于去掉文件名的目录和后缀,对应的dirname命令用于截取目录
示例一: # /usr/bin为获取到的目录[root@local ~]# dirname /usr/bin/sort/usr/bin示例一 # 获取到最后文件名sort[root@local ~]# basename /usr/bin/sortsort示例二 # 去除文件名后缀[root@local ~]# basename /usr/include/stdio.h .hstdio[root@local ~]# basename /usr/include/stdio.h stdio.hstdio.h
!/bin/bash# 跳转到脚本所在目录cd $(dirname "$0") || exit 1# 对上面的脚本的解释$0 当前Shell程序的文件名dirname $0 获取当前Shell程序的路径cd $(dirname $0) 进入当前Shell程序的目录exit 1 如果获取不到则退出脚本
