怎么理解 bash [[]] 判断中的 = 和 =~ 这2个判断呢??

1
2
3
4
5
6
7
8
9
查看 man bash 对 [[ 命令的 =~ 操作符说明如下:

An additional binary operator, =~, is available, with the same precedence as == and !=.
When it is used, the string to the right of the operator is considered an extended regular expression and matched accordingly.
The return value is 0 if the string matches the pattern, and 1 otherwise.
If the regular expression is syntactically incorrect, the conditional expression's return value is 2.

Any part of the pattern may be quoted to force the quoted portion to be matched as a string.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
[[ expression ]]
Return a status of 0 or 1 depending on the evaluation of the conditional expression expression. Expressions are composed of the primaries described below under CONDITIONAL EXPRESSIONS. Word splitting and pathname expansion are not
performed on the words between the [[ and ]]; tilde expansion, parameter and variable expansion, arithmetic expansion, command substitution, process substitution, and quote removal are performed. Conditional operators such as -f
must be unquoted to be recognized as primaries.

When used with [[, the < and > operators sort lexicographically using the current locale.

See the description of the test builtin command (section SHELL BUILTIN COMMANDS below) for the handling of parameters (i.e. missing parameters).

When the == and != operators are used, the string to the right of the operator is considered a pattern and matched according to the rules described below under Pattern Matching, as if the extglob shell option were enabled. The = operator
is equivalent to ==. If the nocasematch shell option is enabled, the match is performed without regard to the case of alphabetic characters. The return value is 0 if the string matches (==) or does not match (!=) the pattern, and 1 oth‐
erwise. Any part of the pattern may be quoted to force the quoted portion to be matched as a string.

An additional binary operator, =~, is available, with the same precedence as == and !=. When it is used, the string to the right of the operator is considered a POSIX extended regular expression and matched accordingly (as in regex(3)).
The return value is 0 if the string matches the pattern, and 1 otherwise. If the regular expression is syntactically incorrect, the conditional expression's return value is 2. If the nocasematch shell option is enabled, the match is per‐
formed without regard to the case of alphabetic characters. Any part of the pattern may be quoted to force the quoted portion to be matched as a string. Bracket expressions in regular expressions must be treated carefully, since normal
quoting characters lose their meanings between brackets. If the pattern is stored in a shell variable, quoting the variable expansion forces the entire pattern to be matched as a string. Substrings matched by parenthesized subexpressions
within the regular expression are saved in the array variable BASH_REMATCH. The element of BASH_REMATCH with index 0 is the portion of the string matching the entire regular expression. The element of BASH_REMATCH with index n is the
portion of the string matching the nth parenthesized subexpression.

Expressions may be combined using the following operators, listed in decreasing order of precedence:

( expression )
Returns the value of expression. This may be used to override the normal precedence of operators.
! expression
True if expression is false.
expression1 && expression2
True if both expression1 and expression2 are true.
expression1 || expression2
True if either expression1 or expression2 is true.

The && and || operators do not evaluate expression2 if the value of expression1 is sufficient to determine the return value of the entire conditional expression.



string1 = string2
True if the strings are equal. = should be used with the test command for POSIX conformance. When used with the [[ command, this performs pattern matching as described above (Compound Commands).


=~ 右边支持正则表达式

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
即,使用 =~ 操作符时,其右边的字符串被认为是一个扩展正则表达式。
扩展之后跟左边字符串进行比较,看左边字符串是否包含指定模式。
注意是包含关系,不是完整匹配。
也就是判断右边的模式是否为左边字符串的子字符串,而不是判断右边的模式是否完全等于左边字符串。

这里面提到一个非常关键的点,在所给的扩展正则表达式中,用引号括起来的部分会被当成字符串,不再被当成正则表达式。
如果 =~ 操作符右边的字符串都用引号括起来,那么表示匹配这个字符串自身的内容,不再解析成正则表达式。

如果想要 =~ 操作符右边的字符串被当成正则表达式来处理,一定不能用引号把整个字符串括起来。
无论是双引号、还是单引号都不要加。
这是常见的使用误区,后面会举例说明。

注意:只有 [[ 命令支持 =~ 操作符,test 命令和 [ 命令都不支持 =~ 操作符。


=或者== 右边支持简单的通配

1
2
在 [[ ]] 中 == 2个等号的是 模式匹配, 模式匹配允许使用通配符,例如bash中常用的 通配符 *、?、[...] 等
在 [[ ]] 中 = 1个等号的是 同上
1
在 [[ ]] 中 =~  这个是正则匹配,和 模式匹配不太一样的。

双 [[]] 方括号

1
2
3
4
双方括号是bash中的语法。推荐这个,脚本里面要统一,所判断都用双方括号。

在 [[ ]] 中 == 2个等号的是右边表达式加上双引号单引号那效果就不一样了
在 [[ ]] 中 = 1个等号的是同上

单 [] 方括号

1
2
3
4
单方括号是 sh 里面的语法
在 [ ] 中 == 2个等号的是 精确的相等的判断,判断字符串是否一模一样
在 [ ] 中 = 1个等号的是 精确的相等的判断,判断字符串是否一模一样

其他补充

关于 glob-style pattern 和 regualar expression 的区别:

https://stackoverflow.com/questions/23702202/what-are-the-differences-between-glob-style-pattern-and-regular-expression

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
raditional glob wildcards support a very narrow set of metacharacters — * is "anything", ? is an arbitrary single character; Bourne shell also supports [a-z123] for a single character out of a set of alternatives, and [!x-z789] any one except those listed.

Regex obviously is much richer, supporting repetitions, and (in ERE) alternation and specific numbers of repetitions. Perl-style regex further extends the formalism to the point where multiple books have been written, and more will be.

Basic regex is not altogether a lot more challenging to program than glob wildcards, and these days, a competent programmer would link to an existing library in either case, anyway.

Many simpler systems don't want to burden their users with the complexity of learning regular expressions — even basic wildcards are a challenge to explain to your average sales guy^W^W person who isn't a full-time computer user.



Regular expressions are used in commands / functions for pattern matching in text. For example in the pattern parameter of grep, or in programming languages.

Globbing is used by shells for matching file and directory names using wildcards. The capabilities of globbing depend on the shell. Bash, for example, supports wildcards like:

More information can be found here

https://en.wikipedia.org/wiki/Glob_(programming)

http://teaching.idallen.com/cst8207/15w/notes/190_glob_patterns.html