If you’ve run across ORA-12727: invalid back reference in regular expression, it’s because you’ve referenced a group (a group is an expression enclosed in parenthesis) either that doesn’t exist, or doesn’t exist yet. There are two common reasons for this mistake.

Referencing A Group Before It Exists

One way to run into this error is to reference a group that either doesn’t exist, or doesn’t yet exist. Here’s an example of referencing a group that doesn’t exist:

select regexp_replace('Moose', '^(M)(o)\3+(se)$', '\1\2\3')
from dual;

Here, we create group 1 (M). Then we create group 2 (o). Next, we reference group 3; but the problem is group 3 does not yet exist at this point of reading the regular expression. You would only be able to reference a group after it’s been created, like this:

select regexp_replace('Moose', '^(M)(o)\2+(se)$', '\1\2\3')
from dual;

The above example is perfectly fine. This is because we’re referencing the second group (o) after it’s been created.

Mis-Typing The Regular Expression

Another reason you might experience this issue is just from a simple typo. Take for example the following query:

select case when regexp_like(stooge, '^[[:alnum:]]+ ([[:alnum:]]+)$')
             then regexp_replace(stooge, '^[[:alnum:]]+ ([[:alnum:]]+)$', '\1')
            when regexp_like(stooge, '^Mrs?\. [[:alnum:]]+ ([[:alnum:]]+)$')
             then regexp_replace(stooge, '^Mrs?\. [[:alnum:]]+ ([[:alnum:]]+)$', '\1')
            when regexp_like(stooge, '^[[:alnum:]]+ [[:alnum:]]\. [[:alnum:]]+$')
             then regexp_replace('^[[:alnum:]]+ [[:alnum:]]\. ([[:alnum:]]+)$', '\1')
       end last_name
from (select 'Moe H. Howard' stooge from dual
      union all
      select 'Mr. Larry Fine' from dual
      union all
      select 'Curley Howard' from dual)

It fails with ORA-12727: invalid back reference in regular expression, simply because the final regexp_replace() function didn’t include the STOOGE column. So the query should read like this:

select case when regexp_like(stooge, '^[[:alnum:]]+ ([[:alnum:]]+)$')
             then regexp_replace(stooge, '^[[:alnum:]]+ ([[:alnum:]]+)$', '\1')
            when regexp_like(stooge, '^Mrs?\. [[:alnum:]]+ ([[:alnum:]]+)$')
             then regexp_replace(stooge, '^Mrs?\. [[:alnum:]]+ ([[:alnum:]]+)$', '\1')
            when regexp_like(stooge, '^[[:alnum:]]+ [[:alnum:]]\. [[:alnum:]]+$')
             then regexp_replace(stooge, '^[[:alnum:]]+ [[:alnum:]]\. ([[:alnum:]]+)$', '\1')
       end last_name
from (select 'Moe H. Howard' stooge from dual
      union all
      select 'Mr. Larry Fine' from dual
      union all
      select 'Curley Howard' from dual )

Free Oracle SQL Tuning Guide

Check out my FREE guide! 7 SQL Tuning Secrets You Can Use Immediately, Even If You’ve Never Tuned a Query In Your Life!

Get it here: tuningsql.com/secrets

7 SQL Tuning Secrets You can Use Immediately, Even If You've Never Tuned A Query In Your Life

Leave a Reply

Your email address will not be published. Required fields are marked *