Ruby gsub 中的正则表达式捕获组

Ruby regex capture groups in gsub

假设我想将邮件中的每个字母切换为反向字母表中的位置。为什么我似乎不能使用捕获的组并在一个 gsub 中完成?

也许有人可以大致解释一下在 gsub 中使用捕获的组,反向引用可以是空的(没有 ' ')吗?我可以使用#{\1}吗?

def decode(message)
  a = ('a'..'z').to_a
  z = a.reverse
  message.gsub!(/([[:alpha:]])/, z[a.index('')]) 
end

decode("the quick brown fox")

请记住,方法的参数会立即求值,并将结果传递给方法。如果你想让换人适应比赛:

message.gsub!(/([[:alpha:]])/) { |m| z[a.index()] }

它使用一个块来评估每个匹配项。

一种方法是操纵 ASCII 值。

def code(message)
  message.gsub(/[[:alpha:]]/) { |s| (((s < 'a') ? 155 : 219 ) - s.ord).chr }
end

coded = code("the quick brown fox")
  #=> "gsv jfrxp yildm ulc" 
code(coded)
  #=> "the quick brown fox" 

注:

'A'.ord + 'Z'.ord
  #=> 155 
'a'.ord + 'z'.ord
  #=> 219 

另一种是使用哈希:

a = ('a'..'z').to_a
Ch = a.zip(a.reverse).to_h
  #=> {"a"=>"z", "b"=>"y",..., "y"=>"b", "z"=>"a"} 

def code(message)
  message.gsub(/[[:alpha:]]/, Ch)
end

coded = code("the quick brown fox")
  #=> "gsv jfrxp yildm ulc"
code(coded)
  #=> "the quick brown fox"

使用gsub:

您的代码无法正常工作,因为 '' 尚未在您需要的时候被评估为其正则表达式匹配。这个可以用block来解决,所以定义match变量:

message.gsub(/[[:alpha:]]/) { |char| z[a.index(char)] }

使用tr:

解决此类问题的更有效方法是 "replacing one set of characters with another set",而不是使用 String#tr。这可以按如下方式完成:

message.tr(a.join(''), z.join(''))