我需要解釋一下原因:
$test=`expr "hello" : "\([a-z]*\)"`; echo $test
將會印出hello
,其中:
$test=`expr "hello" : "hel"`; echo $test
將傳回匹配的字元數。
並且:
$ test=`expr "hello123there" : ".*o\([0-9]*\)"t`; echo $test
.*
請注意,我必須指定它o
返回後123
,否則它不會返回任何內容。
答案1
它就在手冊頁中,EG http://ss64.com/bash/expr.html
模式比對傳回 ( 和 ) 之間符合的字串或 null;如果不使用 ( 和 ),則傳回符合的字元數或 0。
答案2
這就是如何expr
匹配表達式作品。
如果模式至少包含一個正規表示式子表達式,則應傳回[\(...\)]
與反向引用表達式相符的字串。匹配,所以你把它找回來了。\1
hello
\([a-z]*\)
expr
用過的布雷,所以你必須轉義\(
並\)
表示一個子表達式。在 BRE 中使用(
and)
被視為文字。
否則,您將獲得匹配的字元數。
在 中expr "hello123there" : ".*\([0-9]*\)"t
,您傳回了空字串。那是因為正規表示式的貪婪性,將匹配最長的子串。
因為*
匹配零個或多個字符,所以[0-9]*
可以匹配零次,並且.*
會匹配最長的子字串hello123
。這就是為什麼你得到空字串的原因。
如果你有perl
,你可以嘗試:
printf "hello123there" | perl -Mre=debugcolor -ne 'print $1 if /.*([0-9]*)t/'
和:
printf "hello123there" | perl -Mre=debugcolor -ne 'print $1 if /.*o([0-9]*)t/'
看看差異。