string substitution problem

Discussion in 'Perl Misc' started by Dawn Schepleng, Oct 15, 2003.

  1. Hi :)

    I am a novice Perl programmer, and have encountered the following problem.
    I can make the following string substitution work:

    $high_level_dir = "/ceswbl2/installed/bin"
    $low_level_dir = "/ceswbl2/src/sparc/bin";
    $line =~ s{$low_level_dir(/\w+)+/(\w+)}{$high_level_dir/$2};

    This will correctly take a line like:

    /ceswbl2/src/sparc/bin/cec_sim/radar/sps48/cecsimlm

    and make substitutions such that $line then equals:

    /ceswbl2/installed/bin/cecsimlm.

    I'm using \w+ to represent a word with numbers and underscores, and am
    using "(", ")", and "/" to be literal, and using the substitution format of
    "s{}{}" vice "s///" to be more readable.

    However, when I take this working perl substitution and try to invoke it as a
    system call like:

    system("perl -pi -e 's{$low_level_dir(/\w+)+/(\w+)}{$high_level_dir/$2}'
    $real_run_file");

    It no longer works. The error occurs in a first-pass parse of the perl script,
    and says something line "Unrecognized escape \w passed through
    in cepSetGoEnv.pl at line 31".

    With the help of a co-worker, we've tried changing "{" "}" to "|" and we've
    also tried escaping out the "(" and ")" with no luck.

    What is the subtle detail that makes this work in-line, but not when the script
    is run w/i the system call?

    Any ideas would be appreciated!

    Thanks,

    Dawn Schepleng
    JHU/APL
     
    Dawn Schepleng, Oct 15, 2003
    #1
    1. Advertising

  2. [posted & mailed]

    On Wed, 15 Oct 2003, Dawn Schepleng wrote:

    >$high_level_dir = "/ceswbl2/installed/bin"


    Missing semicolon, by the way.

    >$low_level_dir = "/ceswbl2/src/sparc/bin";
    >$line =~ s{$low_level_dir(/\w+)+/(\w+)}{$high_level_dir/$2};


    That works as expected, which is good.

    >system("perl -pi -e 's{$low_level_dir(/\w+)+/(\w+)}{$high_level_dir/$2}'
    > $real_run_file");
    >
    >It no longer works. The error occurs in a first-pass parse of the perl
    >script, and says something line "Unrecognized escape \w passed through in
    >cepSetGoEnv.pl at line 31".


    Right. You've made a double quoted string "perl -pi ..." and it has
    backslashed characters in it. In a *regex*, \w means something. In a
    double-quoted string, it doesn't. You'll need to DOUBLE the backslash.

    print "m/(\\w+)/"; # prints: m/(\w+)/

    The other problem you'll encounter is that Perl interpolates $2 when you
    make that string you pass to system(). You don't want Perl to do that;
    you want Perl to send the literal string '$2' to the system() command so
    that when system() runs perl, perl sees $2.

    system("perl -pi -e 's{foo(/\\w+)+(/\\w+)}bar\$2}' file");

    But here's the nice thing: you don't need to call system() here. The -p
    and -i flags just add wrappers around the code you give. If you know what
    those wrappers look like, you can write a program that DOES what -pi does.
    They're explained in the 'perlrun' manpage:

    perldoc perlrun

    I'm pretty sure there's an exact example of how to do what -pi does in
    your program. Look for the documentation of the -i switch.

    --
    Jeff Pinyan RPI Acacia Brother #734 2003 Rush Chairman
    "And I vos head of Gestapo for ten | Michael Palin (as Heinrich Bimmler)
    years. Ah! Five years! Nein! No! | in: The North Minehead Bye-Election
    Oh. Was NOT head of Gestapo AT ALL!" | (Monty Python's Flying Circus)
     
    Jeff 'japhy' Pinyan, Oct 15, 2003
    #2
    1. Advertising

  3. Also sprach Purl Gurl:

    > Jeff Pinyan wrote:
    >
    >> Dawn Schepleng wrote:

    >
    > (snipped)
    >
    >> system("perl -pi -e 's{foo(/\\w+)+(/\\w+)}bar\$2}' file");

    >
    >
    > Under both perl 5.6 and perl 5.8 this still cops an error message:
    >
    > "Can't do inplace edit without backup."
    >
    > Perhaps this is a bug with cygwin / win32 ports?


    Partly. It's mainly a limitation of Win32 that doesn't allow altering an
    already open file (unless of course you open it solely for changing the
    file).

    A fix would be to have perl make changes to a temporary copy of the
    original file and afterwards do a rename when the -i switch is employed.
    So far the user has to do that on his own.

    Tassilo
    --
    $_=q#",}])!JAPH!qq(tsuJ[{@"tnirp}3..0}_$;//::niam/s~=)]3[))_$-3(rellac(=_$({
    pam{rekcahbus})(rekcah{lrePbus})(lreP{rehtonabus})!JAPH!qq(rehtona{tsuJbus#;
    $_=reverse,s+(?<=sub).+q#q!'"qq.\t$&."'!#+sexisexiixesixeseg;y~\n~~dddd;eval
     
    Tassilo v. Parseval, Oct 15, 2003
    #3
  4. Dawn Schepleng

    Big and Blue Guest

    Jeff 'japhy' Pinyan wrote:

    > The other problem you'll encounter is that Perl interpolates $2 when you
    > make that string you pass to system(). You don't want Perl to do that;
    > you want Perl to send the literal string '$2' to the system() command so
    > that when system() runs perl, perl sees $2.
    >
    > system("perl -pi -e 's{foo(/\\w+)+(/\\w+)}bar\$2}' file");
    >


    Also, Perl will (or may) pass that through a shell. If you don't
    want to deal with ensuring things aren't interpreted by the shell as
    well, then pas system a LIST of arguments, rather than a single string.



    --
    -*- Just because I've written it here doesn't -*-
    -*- mean that you should, or I do, believe it. -*-
     
    Big and Blue, Oct 15, 2003
    #4
  5. Tassilo v. Parseval wrote:
    > Also sprach Purl Gurl:
    >> Under both perl 5.6 and perl 5.8 this still cops an error
    >> message:
    >>
    >> "Can't do inplace edit without backup."
    >>
    >> Perhaps this is a bug with cygwin / win32 ports?

    >
    > Partly. It's mainly a limitation of Win32 that doesn't allow
    > altering an already open file (unless of course you open it solely
    > for changing the file).


    Does that mean that if a Perl program, that makes use of flock() on
    *nix platforms, is run on a Windows platform with flock() disabled,
    you still don't need to worry too much about files being corrupted
    because of concurrent changes?

    --
    Gunnar Hjalmarsson
    Email: http://www.gunnar.cc/cgi-bin/contact.pl
     
    Gunnar Hjalmarsson, Oct 15, 2003
    #5
  6. Purl Gurl wrote:
    > Gunnar Hjalmarsson wrote:
    >> Tassilo v. Parseval wrote:
    >>> Win32 ... doesn't allow altering an already open file (unless
    >>> of course you open it solely for changing the file).

    >>
    >> Does that mean that if a Perl program, that makes use of flock()
    >> on *nix platforms, is run on a Windows platform with flock()
    >> disabled, you still don't need to worry too much about files
    >> being corrupted because of concurrent changes?

    >
    > No. Concurrent writes under Win32 are a problem which must be
    > addressed via semaphore locking or one of my locking mechanisms
    > presented at my website.


    Okay, that's what I thought. Suppose my conclusion out from Tassilo's
    statement was far too extensive. :)

    Btw, flock() works on some Win32 systems. As far as I have understood,
    the need for using some other locking method is limited to Windows 95
    and 98.

    <snip>

    > Perl does not honor "permission denied" under Win32. Locking
    > mechanisms are critical to prevent concurrent writes under Win32
    > when using Perl.


    Thanks for clarifying.

    --
    Gunnar Hjalmarsson
    Email: http://www.gunnar.cc/cgi-bin/contact.pl
     
    Gunnar Hjalmarsson, Oct 15, 2003
    #6
  7. On Wed, 15 Oct 2003, Purl Gurl wrote:

    >system("perl -i.bak -e 's/gurlpurl/purlgurl/e' test.txt") or die "FUBAR $!";
    >
    >Use of a die causes a script to die at that line but does
    >not generate any error message.


    That's because system() returns false on success, not on failure. You
    should either do

    system(...) and die "...";

    or

    system(...) == 0 or die "...";

    --
    Jeff Pinyan RPI Acacia Brother #734 2003 Rush Chairman
    "And I vos head of Gestapo for ten | Michael Palin (as Heinrich Bimmler)
    years. Ah! Five years! Nein! No! | in: The North Minehead Bye-Election
    Oh. Was NOT head of Gestapo AT ALL!" | (Monty Python's Flying Circus)
     
    Jeff 'japhy' Pinyan, Oct 15, 2003
    #7
  8. Jeff 'japhy' Pinyan <> wrote:

    > You
    > should either do
    >
    > system(...) and die "...";
    >
    > or
    >
    > system(...) == 0 or die "...";



    or:

    !system(...) or die "...";


    Which is what I use, because I'm already used to
    writing "somefunc() or die".


    --
    Tad McClellan SGML consulting
    Perl programming
    Fort Worth, Texas
     
    Tad McClellan, Oct 16, 2003
    #8
  9. Dawn Schepleng

    Dave Saville Guest

    On Wed, 15 Oct 2003 14:12:49 -0700, Purl Gurl wrote:

    >Mostly true. WinME is also in there. This problem with flock will
    >appear anytime a "Win32 System" is used. This does not exclude
    >WinNT5 completely. Possibly OS/2 exhibits this problem, not sure.
    >Other candidates would be systems using DR-DOS or IBM DOS.


    FYI flock() works on OS/2, at least with v5.8.0 - Some time ago I
    tested with two scripts as I had the same problem - cgi updating a
    common file. One script held an exclusive lock on a file and then
    waited on keyboard input - the other tried to get the lock and said
    when it did. The latter script just hung until I replied to the first
    and it released the lock.

    Regards

    Dave Saville

    NB switch saville for nospam in address
     
    Dave Saville, Oct 16, 2003
    #9
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Troll
    Replies:
    6
    Views:
    2,437
    Kris Wempa
    Sep 26, 2003
  2. Ed Keith

    Raw string substitution problem

    Ed Keith, Dec 16, 2009, in forum: Python
    Replies:
    1
    Views:
    252
    Chris Hulan
    Dec 16, 2009
  3. Gabriel Genellina

    Re: Raw string substitution problem

    Gabriel Genellina, Dec 16, 2009, in forum: Python
    Replies:
    13
    Views:
    654
  4. Ed Keith
    Replies:
    3
    Views:
    565
    Peter Otten
    Dec 16, 2009
  5. jdwy
    Replies:
    6
    Views:
    112
    Mikael Høilund
    Nov 8, 2008
Loading...

Share This Page