http://www.perlmonks.org?node_id=899025


in reply to perl -pi -e s'/^\s+//'g $file

I often build up proofs-of-concept from one-liners before I finally write them into a "real" script. invaluable to me in this process is perlrun. Perlrun has "actual" code that is equivalent to many of the commandline switches. For instance, under the section for -i[extension]:

From the shell, saying
    $ perl -p -i.orig -e "s/foo/bar/; ... "
is the same as using the program:
#!/usr/bin/perl -pi.orig s/foo/bar/;

which is equivalent to
#!/usr/bin/perl $extension = '.orig'; LINE: while (<>) { if ($ARGV ne $oldargv) { if ($extension !~ /\*/) { $backup = $ARGV . $extension; } else { ($backup = $extension) =~ s/\*/$ARGV/g; } rename($ARGV, $backup); open(ARGVOUT, ">$ARGV"); select(ARGVOUT); $oldargv = $ARGV; } s/foo/bar/; } continue { print; # this prints to original filename } select(STDOUT);

except that the -i form doesn't need to compare $ARGV to $oldargv to know when the filename has changed. It does, however, use ARGVOUT for the selected filehandle. Note that STDOUT is restored as the default output filehandle after the loop.

This is a great starting place for converting your on-liner and also a great place to learn how to do it from scratch the next time.

The only other thing I would urge you to do is not to forget your strictures when you start making it a longer script. your code example:

#!/usr/bin/perl $file="test"; $cmd="perl -pi -e s\'\/^\\s+\/\/'g $file"; print "$cmd\n"; system($cmd);

What I want you to do:
#!/usr/bin/perl use strict; use warnings; $file="test"; $cmd="perl -pi -e s\'\/^\\s+\/\/'g $file"; print "$cmd\n"; system($cmd);


#my sig used to say 'I humbly seek wisdom. '. Now it says:
use strict;
use warnings;
I humbly seek wisdom.

Replies are listed 'Best First'.
Re^2: perl -pi -e s'/^\s+//'g $file
by Anonymous Monk on Apr 12, 2011 at 18:49 UTC
    Having written the exact code once myself, I find it disgusting :P use B::Deparse , then transform the results
    $ perl -MO=Deparse -p -i.orig -e "s/foo/bar/; ... " BEGIN { $^I = ".orig"; } LINE: while (defined($_ = <ARGV>)) { s/foo/bar/; die 'Unimplemented'; } continue { die "-p destination: $!\n" unless print $_; } -e syntax OK
    into a template
    #!/usr/bin/perl -- use strict; use warnings; Main( @ARGV ); exit( 0 ); sub Main { RuinSomeFilesOrig(@_); } sub RuinSomeFilesOrig { local *ARGV; local $^I = ".orig"; local @ARGV = @_; LINE: while (defined($_ = <ARGV>)) { s/foo/bar/; ...; } continue { die "-p destination: $!\n" unless print $_; } }
    then turn it into a distribution with scriptdist :D

      ++


      #my sig used to say 'I humbly seek wisdom. '. Now it says:
      use strict;
      use warnings;
      I humbly seek wisdom.

        Actually you'd need

        local @ARGV = @_; require ARGV::readonly; ARGV::readonly->import; ## THIS!!!

        But if you're going to write all that, which might confuse some, you might as well just steal ARGV::readonly verbatim

        local @ARGV = @_; # Tom Christiansen in Message-ID: <24692.1217339882@chthon> # reccomends essentially the following: for (@ARGV){ s/^(\s+)/.\/$1/; # leading whitespace preserved s/^/< /; # force open for input $_.=qq/\0/; # trailing whitespace preserved & pipes forbidden };

        Actually ARGV::readonly isn't needed with -i.orig (or -pi.orig) because perl does a stat first

        $ perl -pe 1 "echo shabba|" shabba $ perl -Tpe 1 "echo shabba|" Insecure $ENV{PATH} while running with -T switch. $ perl -Tpi.orig -e 1 "echo shabba|" Can't open echo shabba|: Invalid argument.

        Happens around http://perl5.git.perl.org/perl.git/blob?f=doio.c#l897