您的位置:首页 > 其它

sh编写体会,与其它语言习惯比较

2013-04-09 21:08 225 查看
变量赋值
正确
a=kkkk
a="kkkk"
非法,下面这种写法都是因为空格导致linux认为不是在赋值,而是需要执行某个命令,所以会提示命令不存在
a = kkkk
a= kkkk
a= "kkkk"
----------------------------
命令行结束是换行,或是分号;
--------------
双引号""是部分引用字符串,也就是它跟php差不多,里面某些符号将被视为命令而不是字符串
像 "$d kkk"就是 变量$d + kkk的意思
-----------------
单引号''是全部字符串符号,也就是说它里面的字符串全部视为字符串,不会出现命令解析,出现'时需要转义
----------
逗号跟其它语言一样,全部执行,返回最后那节值
-----------------
``号(跟~号同一个键)表示会把命令的运行结果返回,而不是输出,这样就可以把输出赋值到变量了.
同时""符号中也可包含它,意义一样.
-------------
当我们需要空语句时,有时我们是可以使用分号的,但是sh不允许.
我们必须使用冒号

if [ ];then #注意[ ]中间有空格,没有空格认为出错,因为[是一个命令
: # 这里必须使用冒号,不能使用分号,也不能是空的
fi
----------
$ 变量引用
a="这是一个变量值"
echo "$a" #输出上行a的值,
--------------------[]符号----------
if [ 命令 ];then语句中的命令必须跟二边的[]有空格.否则会出错.
----------------------逻辑与写法---------------
if [ 条件1 ] && [ 条件2 ] 这是与
if [ 条件1 ] || [ 条件2 ] 这是或
-----------
----------expr index "$str" $sub --------
第一个字符是从1开始,找不到时返回0
且需要注意的是,它只查找$sub中的首个字母出现的第一次的位置,它并不把整$sub串做为匹配,也就是 你写 abc意思是想找abc这串出现的位置,但是这个它却在123a123abc的3a1这里就认为匹配了.返回了4而不是8.
如果需要匹配可以使用
expr "$str" : '.*\(要找的子串正则\)' ,然后使用 -n 检测是 no null来判断是否存在子串

if [ -n "`expr "$logStr" : '.*\( status=sent \)'`" ];then # is sent ok log
echo "sent log"
注意使用-n时最好使用""把返回字符串包起来,否则会出现很郁闷的问题,不懂它当啥来解释了,反正会出现不管是否包含都是真.
---------------
|管道,它会把符号着处理的结果做为符号后面的命令的输入

ls | grep "输出中是我的行"
然后只有包含 "输出中是我的行"的内容行才会被显示
-------for in--------
for list in $lists;do
echo $list
done

需要注意的是它跟php的foreach有点,$lists必须是一个数组才行.
比如本意想得到本目录下的所有文件(不含子目录)
lists="/var/log"
因为$lists只是一个目录,以数组形式来看话,它只有一个,所以for出来只有它.
必须写成如下,这样它才是表示多组路径
lists="/var/log/*"
-------------------自动移除换得符------------
str=`ps ax` #有换行符
str="echo `ps ax`" #没换行符,关键是echo

----------------------计算方式,非常的奇怪,但是还有另外一个问题,在运算,需要注意int/long类型,这是一个比较郁闷问题-----------
1 #!/bin/bash
2 # 使用10种不同的方法计数到11.
3
4 n=1; echo -n "$n "
5
6 let "n = $n + 1" # let "n = n + 1" 也可以.
7 echo -n "$n "
8
9
10 : $((n = $n + 1))
11 # ":" 是必需的, 因为如果没有":"的话,
12 #+ Bash将会尝试把"$((n = $n + 1))"解释为一个命令.
13 echo -n "$n "
14
15 (( n = n + 1 ))
16 # 上边这句是一种更简单方法.
17 # 感谢, David Lombard, 指出这点.
18 echo -n "$n "
19
20 n=$(($n + 1))
21 echo -n "$n "
22
23 : $[ n = $n + 1 ]
24 # ":" 是必需的, 因为如果没有":"的话,
25 #+ Bash将会尝试把"$[ n = $n + 1 ]"解释为一个命令.
26 # 即使"n"被初始化为字符串, 这句也能够正常运行.
27 echo -n "$n "
28
29 n=$[ $n + 1 ]
30 # 即使"n"被初始化为字符串, 这句也能够正常运行.
31 #* 应该尽量避免使用这种类型的结构, 因为它已经被废弃了, 而且不具可移植性.
32 # 感谢, Stephane Chazelas.
33 echo -n "$n "
34
35 # 现在来一个C风格的增量操作.
36 # 感谢, Frank Wang, 指出这点.
37
38 let "n++" # let "++n" 也可以.
39 echo -n "$n "
40
41 (( n++ )) # (( ++n ) 也可以.
42 echo -n "$n "
43
44 : $(( n++ )) # : $(( ++n )) 也可以.
45 echo -n "$n "
46
47 : $[ n++ ] # : $[ ++n ]] 也可以.
48 echo -n "$n "
49
50 echo
51
52 exit 0

更加详细的用法 http://www.tsnc.edu.cn/default/tsnc_wgrj/doc/abs-3.9.1_cn/html/index.html 或书名
<<高级Bash脚本编程指南>>
----------------------------------------------------------------
----------------删除/替换字符串---------------
移除
str="被查找的字符"
subStr="查找"
reStr="新"
${str##$subStr}
替换
${str/$subStr/$reStr}
这个用法也是有点怪.第一个不要$号
-----------------------
使用sh的函数时要紧记不能递归调用,因为效率太差,如果有必要,最后实现c或是其它外部语言实现后再调用

8999
9000
9001
2011骞?12?21妤 骀涓 17:38:24 CST - 2011骞?12?21妤 骀涓 17:39:50 CST
add log [/var/www/edm/ssh/log/333333] exit
就下面的代码
17:38:24
17:39:50
耗时1分钟.

---------------非内部命令/管道会产生子shell-----------
内部命令会比外部的快

ps ax | grep就会产生子shell
你会发现其实只运行一个sh文件.却出现了二个匹配,这因为是|管道命令产生的子shell
如果需要不让子shell混到ps中去.可以把二个命令分开


fsh=`ps ax`
echo $fsh
echo "$fsh"
fsh=`echo "$fsh" | grep "[0-9]\+ /.*/bash .*/ssh/$shName"`
echo $fsh
------------------------------echo 会移除换行符----------------

fsh=`ps ax`
echo $fsh # 没有了换行
echo "$fsh" #保留着换行
fsh=`echo "$fsh" | grep "[0-9]\+ /.*/bash .*/ssh/$shName"`
echo $fsh

----------函数代码------------------

timea=`date`

callBack(){

echo $1 # index start by 1
if [ "$1" -gt "9000" ] ;then return 0
fi

callBack $(($1 + 1))
}
callBack 1
echo "$timea - `date`"
另,这个9000别改太大,否则会出现不能结束的问题.我不懂是内存不足?还是内存地址边界出现问题?
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: