expr的坑
expr 是用來對數值進行計算的命令,命令的前后參數需要用空格隔開
[root@localhost ~]# whatis expr
expr (1) – evaluate expressions ? ?表達式求值
expr命令被用做表達式求職計算,但是 expr計算的結果為0的時候,將會被認為是錯誤的,不能作為條件判斷的依據
例如:
[root@localhost ~]# expr 1 + 2
3
expr還可以對變量的值進行計算
[root@localhost ~]# n=3;expr $n + 2
5
但命令執行后是否成功呢??
$? 是shell中顯示命令執行結果是否正確的內置變量,如果執行結果的值為0,表示命令正確執行
使用一個未定義的變量試試
[root@localhost ~]# expr $x + 2;echo $?
2
0
坑!
#結果是對的
[root@localhost ~]# expr $y + 0
0
#被判定為命令執行失敗
[root@localhost ~]# echo $?
1
[root@localhost ~]# y=10;expr $y + 0
10
[root@localhost ~]# echo $?
0
原因
expr的執行結果如果是0,將會被 $? 認為命令執行失敗。expr不能輕易用于作為條件判斷,有時候不能當做條件判斷的依據
在expr命令的幫助文檔中有一句描述:Exit ?status ?is ?0 ?if ?EXPRESSION ?is ?neither null nor 0, 1 if EXPRESSION is null or 0, 2 if?EXPRESSION is syntactically invalid, and 3 if an error occurred.
也就是說,如果表達式的執行結果為null或者0,就認為執行的最終結果為1[命令執行失敗],否則為0[命令執行成功]
類似的情況
let的坑
[root@localhost ~]# i=0;let i++;echo $?
1
[root@localhost ~]# i=0;let ++i;echo $?
0
[root@localhost ~]# let m=0;echo $?
1
查一下let的幫助
help let
和expr類似的情況
Exit Status:If the last ARG evaluates to 0, let returns 1; let returns 0 otherwise.
[root@localhost ~]# i=10;j=-10;
[root@localhost ~]# let sum=i+j
執行結果是對的,但被判定為執行命令失敗
[root@localhost ~]# echo $sum
0
[root@localhost ~]# echo $?
1
例如想計算出兩個數的值就輸出,則會出現不能成功輸出計算得出值得情況,就是因為前一條命令被判定為執行失敗,使用短路與的命令,后續不執行導致的,所以,只能把一條命令拆成2條命令去寫
[root@localhost ~]# let sum=i+j && echo $sum
[root@localhost ~]# let sum=i+j ;echo $sum
0
用于條件判斷的命令如果不嚴謹,將會導致一些無法預料的事情發生!
在做變量測試時候遇到的另一個坑
test命令
- 長格式的例子:
test “$A” == “$B” && echo “Strings are equal”
test “$A” -eq?“$B” && echo “Integers are equal”
- 簡寫格式的例子:
[ “$A” == ?“$B” ] && echo “Strings are equal”
[ “$A” -eq “$B” ] && echo “Integers are equal”
[root@localhost ~]# whatis test
test (1) ????????????– check file types and compare values ? ? ? ?檢查文件類型和值進行比較
[root@localhost ~]# help test
test: test [expr]
Evaluate conditional expression.
其中有一個參數
-n STRING
STRING True if string is not empty. ? ? ? ?如果字符串不為空表示為真
test的坑
測試成功返回0.測試失敗返回255以內的數
[$name 是一個不存在的變量]
[root@localhost ~]# [ -n $name ]? ? ? ? ? ? 為空的變量測試為真???what??
[root@localhost ~]# echo $?
0? ? ? ? ? ?竟然 測試成功
[root@localhost ~]# echo $name ? ? ? ? ? ?$name沒有值
[root@localhost ~]# name=wang? ? ? ? ? ? 給$name 賦值
[root@localhost ~]# [ -n $name ]? ? ? ? ? ? 測試[如果變量不為空則為true]
[root@localhost ~]# echo $?
0? ? ? ? ? ? OK,沒問題
[root@localhost ~]# unset name? ? ? ? ? ? 刪除$name變量,此時$name的值為空,測試時應該表現為假才對
[root@localhost ~]# [ -n $name ]? ? ? ? ? ? ???不對了
[root@localhost ~]# echo $?
0? ? ? ? ? ? 刪除變量$name后,此時測試應該表現為失敗,返回其他數字
[root@localhost ~]# test -n $name;echo $?
0
[root@localhost ~]# [[ -n $name ]]
[root@localhost ~]# echo $?
1
[root@localhost ~]# echo $name
#由于之前已經刪掉了$name變量的值,所以已經為空,不為空表示為真,為空表現為假,所以一下的測試都是失敗的
[root@localhost ~]# [ -n “$name”?]? ? ? ? ? ? 加上雙引號進行測試
[root@localhost ~]# echo $?
1 ? ? ? ? ? 由于已經unset掉了$name,所以測試的語句的返回值是其他數,這里是對的
[root@localhost ~]# test -n “$name” ? ? ? ? ? ?加上引號測試變量
[root@localhost ~]# echo $?
1? ? ? ? ? ? 由于已經unset掉了$name,所以測試的語句的返回值是其他數,這里是對的
不加引號,判斷出來全是真,這是一個坑!坑!坑!
本文來自投稿,不代表Linux運維部落立場,如若轉載,請注明出處:http://www.www58058.com/88818