Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Swapping letters with regexp

Tags:

How can I swap the letter o with the letter e and e with o?

I just tried this but I don't think this is a good way of doing this. Is there a better way?

my $str  = 'Absolute force'; $str =~ s/e/___eee___/g; $str =~ s/o/e/g; $str =~ s/___eee___/o/g; 

Output: Abseluto ferco

like image 609
user3544092 Avatar asked Apr 17 '14 12:04

user3544092


People also ask

Can regex replace characters?

RegEx makes replace ing strings in JavaScript more effective, powerful, and fun. You're not only restricted to exact characters but patterns and multiple replacements at once.

How does regex replace work?

The REGEXREPLACE( ) function uses a regular expression to find matching patterns in data, and replaces any matching values with a new string. standardizes spacing in character data by replacing one or more spaces between text characters with a single space.

What does \\ mean in regex?

\\. matches the literal character . . the first backslash is interpreted as an escape character by the Emacs string reader, which combined with the second backslash, inserts a literal backslash character into the string being read. the regular expression engine receives the string \.

How do you use wildcards in regex?

In regular expressions, the period ( . , also called "dot") is the wildcard pattern which matches any single character. Combined with the asterisk operator . * it will match any number of any characters.


2 Answers

Use the transliteration operator:

$str =~ y/oe/eo/; 

E.g.

$ echo "Absolute force" | perl -pe 'y/oe/eo/' Abseluto ferco 
like image 78
Adrian Frühwirth Avatar answered Sep 20 '22 19:09

Adrian Frühwirth


As has already been said, the way to do this is the transliteration operator

tr/SEARCHLIST/REPLACEMENTLIST/cdsr

y/SEARCHLIST/REPLACEMENTLIST/cdsr

Transliterates all occurrences of the characters found in the search list with the corresponding character in the replacement list. It returns the number of characters replaced or deleted. If no string is specified via the =~ or !~ operator, the $_ string is transliterated.

However, I want to commend you on your creative use of regular expressions. Your solution works, although the placeholder string _ee_ would've been sufficient.

tr is only going to help you for character replacements though, so I'd like to quickly teach you how to utilize regular expressions for a more complicated mass replacement. Basically, you just use the /e tag to execute code in the RHS. The following will also do the replacement you were aiming for:

my $str  = 'Absolute force';  $str =~ s/([eo])/$1 eq 'e' ? 'o' : 'e'/eg;  print $str; 

Outputs:

Abseluto ferco 

Note how the LHS (left hand side) matches both o and e, and them the RHS (right hand side) does a test to see which matched and returns the opposite for replacement.

Now, it's common to have a list of words that you want to replace, so it's convenient to just build a hash of your from/to values and then dynamically build the regular expression. The following does that:

my $str  = 'Hello, foo. How about baz? Never forget bar.';  my %words = (     foo  => 'bar',     bar  => 'baz',     baz  => 'foo', ); my $wordlist_re = '(?:' . join('|', map quotemeta, keys %words) . ')';  $str =~ s/\b($wordlist_re)\b/$words{$1}/eg; 

Outputs:

Hello, bar. How about foo? Never forget baz. 

This above could've worked for your e and o case, as well, but would've been overkill. Note how I use quotemeta to escape the keys in case they contained a regular expression special character. I also intentionally used a non-capturing group around them in $wordlist_re so that variable could be dropped into any regex and behave as desired. I then put the capturing group inside the s/// because it's important to be able to see what's being captured in a regex without having to backtrack to the value of an interpolated variable.

like image 27
Miller Avatar answered Sep 19 '22 19:09

Miller