lxf1992521
lxf1992521

Reputation: 23

How to use bash(3.2.25)'s An additional binary operator:=~

I feel confused about how to use "=~" when I read the info of bash(3.2.25) at rhel5.5

# match the IP, and return true
[kevin@server1 shell]# [[ 192.168.1.1 =~ "^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$" ]] && echo ok || echo fail
ok

# add double qoute
# return false, en ... I know.
[kevin@server1 shell]# [[ 192.168 =~ "^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$" ]] && echo ok || echo fail
fail

# remove double qoute
# return ture ? Why ?
[kevin@server1 shell]# [[ 192.168 =~ ^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$ ]] && echo ok || echo fail
ok 

So, should I qoute the string to the right of the operator ?
And why the second command return true,apparently it should return false !

Here is what the info said:

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 (as in regex3)). 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 shell optionnocasematch' (see the description of shopt' in *Note Bash Builtins::) is enabled, the match is performed without regard to the case of alphabetic characters. Substrings matched by parenthesized subexpressions within the regular expression are saved in the array variableBASH_REMATCH'. The element of BASH_REMATCH' with index 0 is the portion of the string matching the entire regular expression. The element ofBASH_REMATCH' with index N is the portion of the string matching the Nth parenthesized subexpression.

Upvotes: 1

Views: 128

Answers (2)

Rafael Saraiva
Rafael Saraiva

Reputation: 948

Not relevant to the operator itself, however, your regular expression is not limiting each byte of the IP address being matched to be between 0-255. That regex will accept IP's such as: 999.999.999.999.

Please do consider using the following:

^(([01]?\d\d?|2[0-4]\d|25[0-5])\.){3}([01]?\d\d?|2[0-4]\d|25[0-5])$

This will match between 0.0.0.0 and 255.255.255.255. I use this is regex in java but i do believe the syntax to be the same. If not please do tell.

Upvotes: 0

Tom Fenech
Tom Fenech

Reputation: 74595

The recommended, most widely compatible way of dealing with regular expression patterns is to declare them separately, in single quotes:

$ re='^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$'
$ [[ 192.168.1.1 =~ $re ]] && echo ok || echo fail 
ok
$ [[ 192.168 =~ $re ]] && echo ok || echo fail 
fail

Some discussion on the differences in behaviour across bash versions can be found on Greg's Wiki - the take-home message is that using an unquoted variable is the best way to do it.

Upvotes: 1

Related Questions