How to make a Bash switch case match multiple numb

2019-03-09 06:28发布

问题:

I'm running switch case with column number, my column numbers can be 0 -50. When run in loop - they get validated. Now each case supports discrete column number and I observe it's failure. Example: my column number is 10, and here is the code -

    i=10
    a=1
    b=0.65
    if [ "$a" != "$b" ] ; then 
       case $i in  
            [1]|[2]|[5]) echo "Not OK"; ;; 
            [9-10]|[12]) echo "may be ok"; ;; 
            *) echo "no clue - $i"; ;; 
       esac; 
   fi

I expect "may be ok" but get no clue - 10

回答1:

Bash case doesn't work with numbers ranges. [] is for shell patterns.

for instance this case [1-3]5|6) will work for 15 or 25 or 35 or 6.

Your code should look like this:

i=10
a=1
b=0.65
if [ "$a" != "$b" ] ; then
   case $i in
        1|2|5) echo "Not OK"; ;;
        9|10|12) echo "may be ok"; ;;
        *) echo "no clue - $i"; ;;
   esac;
fi

If i can be real between 9 and 10 then you'll need to use if (instead of case) with ranges.



回答2:

if and [ solution

arg=1
if [ "$arg" -lt 5 ]; then
  echo 'less than 5'
elif [ "$arg" -lt 15 ]; then
  echo 'less than 15'
elif [ "$arg" -eq 17 ] || [ "$arg" -eq 19 ]; then
  echo '17 or 19'
else
  echo 'neither'
fi

POSIX 7

Bash follows POSIX as mentioned by https://stackoverflow.com/a/25482040/895245

Here is the quote: http://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html#tag_18_01 section "Case Conditional Construct":

The conditional construct case shall execute the compound-list corresponding to the first one of several patterns (see Pattern Matching Notation) [...] Multiple patterns with the same compound-list shall be delimited by the '|' symbol. [...]

The format for the case construct is as follows:

case word in
     [(] pattern1 ) compound-list ;;
     [[(] pattern[ | pattern] ... ) compound-list ;;] ...
     [[(] pattern[ | pattern] ... ) compound-list]
  esac

and then http://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html#tag_18_13 section "2.13. Pattern Matching Notation" says:

[ If an open bracket introduces a bracket expression as in XBD RE Bracket Expression

and extended regular expressions points to section "9.3.5 RE Bracket Expression" which says:

A bracket expression (an expression enclosed in square brackets, "[]" ) is an RE that shall match a specific set of single characters, and may match a specific set of multi-character collating elements, based on the non-empty set of list expressions contained in the bracket expression.

So only individual characters are considered when you do something like:

[9-10]