in reply to Re: How to make these reg exp changes?
in thread How to make these reg exp changes?

$ perl -wle' my %neg = ( o => "i", i => "o" ); while (<>) { chomp; s/([io])(M*)(\.+)/ $1.$2.( $neg{$1} x length($3) ) /eg; s/(\.+)(?=M*([io]))/ $neg{$2} x length($1) /eg; print; } ' ....MMMMiiii ....MMMMoooo iiiiMMMM.... ooooMMMM.... ooooMMMMiiii iiiiMMMMoooo iiiiMMMMoooo ooooMMMMiiii

Simpler version that only works with Perl 5.10+:

$ perl -wle' my %neg = ( o => "i", i => "o" ); while (<>) { chomp; s/([io])M*\K(\.+)/ $neg{$1} x length($2) /eg; s/(\.+)(?=M*([io]))/ $neg{$2} x length($1) /eg; print; } ' ....MMMMiiii ....MMMMoooo iiiiMMMM.... ooooMMMM.... ooooMMMMiiii iiiiMMMMoooo iiiiMMMMoooo ooooMMMMiiii

I could have used -p above, but I wanted to make clear that %neg only needs to be initialized once without complicating the issue by adding a BEGIN. Here's the 5.10+ version using -p:

perl -ple' BEGIN { %neg = qw( i o o i ) } s/([io])M*\K(\.+)/ $neg{$1} x length($2) /eg; s/(\.+)(?=M*([io]))/ $neg{$2} x length($1) /eg; '

Update: Added \K version. \K rocks.
Update: Added explanation about -p.

Replies are listed 'Best First'.
Re^3: How to make these reg exp changes?
by Anonymous Monk on Nov 16, 2009 at 00:09 UTC
    exactly what I was looking for... The trick with the hash was just the thing!
    Thank you very much!
      Honestly, the hash has nothing to do with the problem.
      $neg{$1}
      is just short for
      ($1 eq 'o' ? 'i' : 'o')
      weird?
      $s='III...MMMMMOOOO....MMMIIII'; print $s."\n"; %neg = ( O => "I", I => "O" ); $s=~s/([IO])(M*)(\.+)/ $1.$2.( $neg{$1} x length($3) ) /eg; $s=~s/(\.+)(?=M*([IO]))/ $neg{$2} x length($1) /eg; print $s;print "\n"; <code> It prints:<br> <code> III...MMMMMOOOO....MMMIIII IIIOOOMMMMMOOOOIIIIMMMIIII

        You told us that if the "." is not the first character, one should look back. Are you saying that's wrong?

        If you actually want to look to the other side of the adjacent Ms,

        perl -wle' my %neg = ( O => "I", I => "O" ); $_ = "III...MMMMMOOOO....MMMIIII"; print; s/([IO])(M+)(\.+)/ $1.$2.( $neg{$1} x length($3) ) /eg; s/(\.+)(?=M+([IO]))/ $neg{$2} x length($1) /eg; print; '