Beefy Boxes and Bandwidth Generously Provided by pair Networks
laziness, impatience, and hubris
 
PerlMonks  

Re^4: Slurping search-replace patterns from a file

by moritz (Cardinal)
on Oct 14, 2008 at 17:47 UTC ( [id://717054]=note: print w/replies, xml ) Need Help??


in reply to Re^3: Slurping search-replace patterns from a file
in thread RESOLVED: Slurping search-replace patterns from a file

Hope I didn't miss anything...

That's the crucial point: You never know. Perl is a language with a very complex syntax (compared to all other programming languages that I know of) that you can basically never be sure if you approach things in this way.

I thought I was quite confident with Perl's syntax, until I found out that you can have whitespaces between the sigil and the variable, and that even works in string interpolation:

$ perl -wle 'my $x = 3; print "x: $ x"' x: 3

I certainly didn't expect that.

What I learned from this is to never assume that you know every detail of Perl syntax, so I won't be sure that I've covered all corner cases. Can you be?

Replies are listed 'Best First'.
Re^5: Slurping search-replace patterns from a file
by gone2015 (Deacon) on Oct 14, 2008 at 20:14 UTC
    What I learned from this is to never assume that you know every detail of Perl syntax, so I won't be sure that I've covered all corner cases. Can you be?

    I would not presume.

    AFAIK the only characters that trigger interpolation are '$' and '@'. But, as you say, with Perl it's unsafe to assume that anything can be depended on.

    However, if we can trust that much, then escaping '$' unless it's followed by a digit only lets past stuff which is supposed to be safe. And escaping '@' unconditionally seems to cover that. Unless there's some other magic that throws the escaping mechansm.

    <sigh>

    I suppose one could fall back on a hand affair:

    use strict ; use warnings ; while (<DATA>) { my ($pat, $repl) = (split '/') [1, 2]; my $s = "foo" ; printf "%40s '%s' -> ", "/$pat/$repl/", $s ; my @trap = $s =~ m/$pat/ ; $repl =~ s/(?<!\\)((?:\\\\)*)\$([1-9])/(defined($1) ? $1 : '') .(defined($trap[$2-1]) ? $tra +p[$2-1] : '')/eg ; $s =~ s/$pat/$repl/ ; print "'$s'\n" ; } __DATA__ s/foo/bar/ s/(fo)o/bar$1/ s/(fo)o/bar\$1/ s/(fo)o/bar\\$1/ s/oo/${system "echo hello sailor !"}/ s/oo/@{system "echo hello sailor !"}/
    which only attempts to simulate '$1'..'$9' -- but that may be sufficient. Of course, String::Interpolate may well do a more complete job.

    Unless, of course, there's some other gotcha...

      Wow, that was clever but a bit beyond my needs. I ended up using the code you posted in your previous message and it's working perfectly.

      The possible security risks of some obscure escape circumvention are, for me, less important than the performance hit of manually storing and retrieving the backreferences.

      Thanks again.

      -HKS

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: note [id://717054]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others studying the Monastery: (2)
As of 2026-01-17 16:15 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?
    What's your view on AI coding assistants?





    Results (121 votes). Check out past polls.

    Notices?
    hippoepoptai's answer Re: how do I set a cookie and redirect was blessed by hippo!
    erzuuliAnonymous Monks are no longer allowed to use Super Search, due to an excessive use of this resource by robots.