I’m having trouble capturing the digits in a string of this format (t|b|bug_|task_|)1234 using a bash regex. The below doesn’t work:
[[ $current_branch =~ ^(t|b|bug_|task_|)([0-9]+) ]]
But once I change it to something like this:
[[ $current_branch =~ ^(t|b|bug_|task_)([0-9]+) ]]
it works, but of course its wrong because it doesn’t cover the case where there are no prefixes. I realize in this case I could do
[[ $current_branch =~ ^(t|b|bug_|task_)?([0-9]+) ]]
and achieve the same result, but I’d like to know why the 2nd example doesn’t work. That regex seems to work fine in Ruby, for example.
(This is on GNU bash, version 3.2.48(1)-release (x86_64-apple-darwin11), OSX Lion)
I’m certain that the difference between working and non-working versions of the regex are based in the different ways of reading
regex (7). I’m going to quote the whole relevant part, because I think it goes to the heart of your issue:OK, there’s quite a lot here to unpack. First of all, note that the “(!)” symbol means that there is an open or non-portable issue.
The essential issue is in the very next paragraph:
Your case is that you have an empty branch. As you can see from the “(!)”, the empty branch is an open or non-portable issue. I think this is why it works on some systems but not on others. (I tested it on Cygwin 4.1.10(4)-release, and it did not work, then on Linux 3.2.25(1)-release, and it did. The two systems have equivalent, but not identical, man pages for regex7.)
Assuming that branches must be nonempty, a branch can be a piece, which can be an atom.
An atom can be “an empty set of “()” (matching the null string)(!)”.
<sarcasm>Well, that’s really helpful.</sarcasm>So, POSIX specifies a regular expression for the empty string, i.e.(), but also appends a “(!)”, to say that this is an open issue, or not portable.Since what you’re looking for is a branch that matches the empty string, try
which uses the
()regex to match the empty string. (This worked for me in my Cygwin 4.1.10(4)-release shell, where your original regex didn’t.)However, while (hopefully) this suggestion will work for you in your current setup, there’s no guarantee that it will be portable. Sorry to disappoint.