Perl Regex ‘e’ (eval) modifier with s///

It’s not exactly a “simple” question, so don’t beat yourself up.

The issue is that with a single /e, the RHS is understood to be code whose eval’d result is used for the replacement.

What is that RHS? It’s $1. If you evaluated $1, you find that contains the string $var. It does not contain the contents of said variable, just $ followed by a v followed by an a followed by an r.

Therefore you must evaluate it twice, once to turn $1 into $var, then again to turn the previous result of $var into the string "testing". You do that by having the double ee modifier on the s operator.

You can check this pretty easily by running it with one /e versus with two of them. Here’s a demo a both, plus a third way that uses symbolic dereferencing — which, because it references the package symbol table, works on package variables only.

use v5.10;

our $str = q(In this string we are $var the "e" modifier.);
our $var = q(testing);

V1: {
    local $_ = $str; 
    s/(\$\w+)/$1/e;
    say "version 1: ", $_;

}

V2: {
    local $_ = $str;
    s/(\$\w+)/$1/ee;
    say "version 2: ", $_;
}

V3: {
    no strict "refs";
    local $_ = $str;
    s/\$(\w+)/$$1/e;
    say "version 3: ", $_;
}

When run, that produces:

version 1: In this string we are $var the "e" modifier.
version 2: In this string we are testing the "e" modifier.
version 3: In this string we are testing the "e" modifier.

Leave a Comment

Hata!: SQLSTATE[HY000] [1045] Access denied for user 'divattrend_liink'@'localhost' (using password: YES)