使用红宝石正则表达式查找单词

问题描述 投票:0回答:2

我找不到符合行开始的特殊词的词。例如;

迈克喜欢香蕉、奇异果和葡萄。
玛丽喜欢香蕉、苹果和西瓜。

我弄错了玛丽最喜欢的水果。我想把

banana
改成
orange
。但是如何才能找到
banana
只从Mary 行开始。我需要红宝石正则表达式,因为我在厨师食谱中使用它。

之前;
Mike 喜欢香蕉、奇异果和葡萄。
玛丽喜欢香蕉、苹果和西瓜。

之后;
Mike 喜欢香蕉、奇异果和葡萄。
玛丽喜欢橙子、苹果和西瓜。

最好的问候
哈桑

regex ruby chef-infra cookbook
2个回答
0
投票

您可以使用正向后视,如下所示

输入

a = "Mike likes banana, kiwi and grapes.
Mary likes banana, apple and watermelon."

输出

p a.gsub(/(?<=Mary .\*\s)banana/,"orange")
#=>"Mike likes banana, kiwi and grapes.
#=> Mary likes orange, apple and watermelon."

或者不使用正则表达式

str = "Mike likes banana, kiwi and grapes. Mary likes banana, apple and watermelon."

“迈克喜欢香蕉、奇异果和葡萄。 玛丽喜欢香蕉、苹果和西瓜。”

str = str
        .lines
        .map(&:strip)
        .map { |line| line.start_with?('Mary') ? line.gsub('banana', 'Orange') : line }
        .join("\n")

p str

输出

"Mike likes banana, kiwi and grapes.
Mary likes Orange, apple and watermelon."

0
投票

我们可以构建方法

def sub_word(str, person, word, replacement)
  str.sub(/^(?=.*\b#{person}\b).*\K\b#{word}\b/, replacement)
end

我将展示几个例子,其中字符串的第一行(

str
)和最后三个参数是固定的,即

f           = "Mike likes banana, kiwi and grapes.\n"
person      = "Mary"
word        = "banana"
replacement = "orange"

书写方便

args        = ["Mary", "banana", "orange"]

示例中唯一变化的是字符串的第二行,(包含

"Mary"
)。

考虑的例子如下。

sub_word(f + "Mary likes banana, apple and melon.", *args)
  #=> "Mike likes banana, kiwi and grapes.\nMary likes orange, apple and melon."
sub_word(f + "Mary likes apple, banana and melon.", *args)
  #=> "Mike likes banana, kiwi and grapes.\nMary likes apple, orange and melon."
sub_word(f + "Yes, Mary is fond of apple, banana and melon.", *args)
  #=> "Mike likes banana, kiwi and grapes.\nYes, Mary is fond of apple, orange and melon."
sub_word(f + "Apple, banana and melon are liked by Mary.", *args)
  #=> "Mike likes banana, kiwi and grapes.\nApple, orange and melon are liked by Mary."
sub_word(f + "Mary likes pear, apple and melon.", *args)
  #=> "Mike likes banana, kiwi and grapes.\nMary likes pear, apple and melon."
sub_word(f + "Maryann likes banana, apple and melon.", *args)
  #=> "Mike likes banana, kiwi and grapes.\nMaryann likes banana, apple and melon."
sub_word(f + "Mary likes bananas, apple and melon.", *args)
  #=> "Mike likes banana, kiwi and grapes.\nMary likes bananas, apple and melon."

在所有示例中,String#sub 使用的正则表达式的计算结果如下。

/^(?=.*\b#{person}\b).*\K\b#{word}\b/
  #=> /^(?=.*\bMary\b).*\K\bbanana\b/

表达式的元素如下

^            match the beginning of a line
(?=          begin a positive lookahead
  .*         match zero or more characters other than line terminators,
             as many as possible
  \bMary\b   match 'Mary' with word boundaries before and after
)            end positive lookahead
.*           match zero or more characters other than line terminators,
             as many as possible
\K           reset the starting point of the reported match and exclude
             any previously consumed characters in the final match
\bbanana\b   match 'banana' with word boundaries before and after

请注意,positive lookahead断言字符串

"Mary"
在行中的某处。

© www.soinside.com 2019 - 2024. All rights reserved.