如何计算一个字符串元素在 ruby​​ 中另一个字符串中的出现次数?

Igg*_*ggy 3 ruby string

如何检查一个短语在字符串中出现的次数?

例如,假设短语是 donut

str1 = "I love donuts!"
#=> returns 1 because "donuts" is found once.
str2 = "Squirrels do love nuts" 
#=> also returns 1 because of 'do' and 'nuts' make up donut
str3 = "donuts do stun me" 
#=> returns 2 because 'donuts' and 'do stun' has all elements to make 'donuts'
Run Code Online (Sandbox Code Playgroud)

我检查了这个建议使用include的SO,但它只有donuts在按顺序拼写时才有效。

我想出了这个,但是在拼写了所有元素之后它不会停止拼写"donuts"。IE"I love donuts" #=> ["o", "d", "o", "n", "u", "t", "s"]

def word(arr)
  acceptable_word = "donuts".chars
  arr.chars.select { |name| acceptable_word.include? name.downcase }
end
Run Code Online (Sandbox Code Playgroud)

如何检查donuts给定字符串中出现了多少次?没有边缘情况。输入永远是String,没有零。如果它只包含元素,donut则不应计为 1 次;它需要包含donuts,不必按顺序排列。

Car*_*and 5

代码

def count_em(str, target)
  target.chars.uniq.map { |c| str.count(c)/target.count(c) }.min
end
Run Code Online (Sandbox Code Playgroud)

例子

count_em "I love donuts!", "donuts"                      #=> 1
count_em "Squirrels do love nuts", "donuts"              #=> 1
count_em "donuts do stun me", "donuts"                   #=> 2
count_em "donuts and nuts sound too delicious", "donuts" #=> 3
count_em "cats have nine lives", "donuts"                #=> 0
count_em "feeding force scout", "coffee"                 #=> 1
count_em "feeding or scout", "coffee"                    #=> 0

str = ("free mocha".chars*4).shuffle.join
  # => "hhrefemcfeaheomeccrmcre eef oa ofrmoaha "
count_em str, "free mocha"
  #=> 4
Run Code Online (Sandbox Code Playgroud)

解释

为了

str = "feeding force scout"
target = "coffee"

a = target.chars
  #=> ["c", "o", "f", "f", "e", "e"] 
b = a.uniq
  #=> ["c", "o", "f", "e"] 
c = b.map { |c| str.count(c)/target.count(c) }
  #=> [2, 2, 1, 1] 
c.min
  #=> 1 
Run Code Online (Sandbox Code Playgroud)

在计算中c,考虑b传递给块并分配给块变量的第一个元素c

c = "c"
Run Code Online (Sandbox Code Playgroud)

然后块计算是

d = str.count(c)
  #=> 2 
e = target.count(c)
  #=> 1
d/e
  #=> 2
Run Code Online (Sandbox Code Playgroud)

这表明str包含足够"c"的 来匹配“咖啡”两次。

要获得的其余计算c是类似的。

附录

如果str匹配字符的字符target必须与 的字符顺序相同target,则可以使用以下正则表达式。

target = "coffee"

r = /#{ target.chars.join(".*?") }/i
  #=> /c.*?o.*?f.*?f.*?e.*?e/i

matches = "xcorr fzefe yecaof tfe erg eeffoc".scan(r)
  #=> ["corr fzefe ye", "caof tfe e"]
matches.size
  #=> 2

"feeding force scout".scan(r).size
  #=> 0 
Run Code Online (Sandbox Code Playgroud)

需要正则表达式中的问号才能使搜索变得非贪婪。