From the Ruby documentation:
Similarly, \&
, \'
, \`
, and \+
correspond to special variables, $&
, $'
, $`
, and $+
, respectively.
And here, the documentation goes on to say:
$~
is equivalent to ::last_match;
$&
contains the complete matched text;
$`
contains string before match;
$'
contains string after match;
$1
, $2
and so on contain text matching first, second, etc capture group;
$+
contains last capture group.
Example:
m = /s(\w{2}).*(c)/.match('haystack') #=> #<MatchData "stac" 1:"ta" 2:"c">
$~ #=> #<MatchData "stac" 1:"ta" 2:"c">
Regexp.last_match #=> #<MatchData "stac" 1:"ta" 2:"c">
$& #=> "stac"
# same as m[0]
$` #=> "hay"
# same as m.pre_match
$' #=> "k"
# same as m.post_match
$1 #=> "ta"
# same as m[1]
$2 #=> "c"
# same as m[2]
$3 #=> nil
# no third group in pattern
$+ #=> "c"
# same as m[-1]
So, \'
in a substitution replacement string has a special meaning. It means "The portion of the original string after the match" - which, in this case, is "bc"
.
So rather than getting \'Bbc
, you get bcBbc
Therefore unfortunately, in this odd scenario, you'd need to double-escape the backslashes:
puts 'abc'.sub('a',"\\\\'B") => "\'Bbc"