bug-coreutils
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

bug#24800: expr 8.25 seems to treat 0 in character class in paren incorr


From: Assaf Gordon
Subject: bug#24800: expr 8.25 seems to treat 0 in character class in paren incorrectly
Date: Wed, 26 Oct 2016 12:42:40 -0400
User-agent: Mozilla/5.0 (X11; Linux x86_64; rv:45.0) Gecko/20100101 Thunderbird/45.3.0

Hello,

On 10/26/2016 12:15 PM, Paul Eggert wrote:
There's no bug here: "expr E" exits with status 1 if E evaluates to 0, and expressions 
like "0 : '\([0-9]\)$'" do evaluate to 0.

Worth mentioning that this is a known "gotcha", explained here:
  http://www.pixelbeat.org/docs/coreutils-gotchas.html#expr

And to elaborate as to why, consider the same regex without grouping - 'expr' 
will return the *number of characters matched*,
so:

    $ expr 0 : '[0-9]$'
    1
    $ expr 1 : '[0-9]$'
    1
    $ expr 4 : '[0-9]$'
    4
    $ expr 9 : '[0-9]$'
    1
    $ expr a : '[0-9]$'
    0

Because you've added grouping, 'expr' returns the *actual matched characters*:

    $ expr 0 : '\([0-9]\)$'
    0
    $ expr 1 : '\([0-9]\)$'
    1
    $ expr 4 : '\([0-9]\)$'
    4
    $ expr 9 : '\([0-9]\)$'
    9
    $ expr a : '\([0-9]\)$'
    [[ empty string ]]


And the "gotcha" is that 'expr' uses the resulting value as exit code. If the value is 
the string "0" or the value 0 or an empty string - the exit code will be 1 (failure). In 
your example, the exit code should not be used to distinguish between matched '0' and non-matching 
string:

    $ expr 0 : '\([0-9]\)$' ; echo $?
    0
    1
    $ expr a : '\([0-9]\)$' ; echo $?
1

Instead, if you use grouping, save the result into a variable and check if it's 
empty:

    $ A=$(expr 0 : '\([0-9]\)$')
    $ test -n "$A" && echo "matched" || echo "did not match"
    matched



regards,
 - assaf















reply via email to

[Prev in Thread] Current Thread [Next in Thread]