如何计算一个字符串元素在ruby中另一个字符串中的出现?
如何检查字符串中出现短语的次数?如何计算一个字符串元素在ruby中另一个字符串中的出现?
例如,让我们说这句话是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'
我检查建议使用包括this SO,但如果是为了阐明它才会起作用。
我想出了这个,但它不会停止拼写所有元素"donuts"
拼写。即"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
如何检查一个给定的字符串中如何许多发生在那里?没有边缘情况。输入将始终为String
,不可为零。如果它包含donut
的元素,则不应将其计为1次;它需要包含,并不是必须的。
代码
def count_em(str, target)
target.chars.uniq.map { |c| str.count(c)/target.count(c) }.min
end
实例
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
说明
对于
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
在计算c
,考虑传递给块和分配给该块变量c
的b
第一个元素。
c = "c"
则该块计算是
d = str.count(c)
#=> 2
e = target.count(c)
#=> 1
d/e
#=> 2
这表明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
正则表达式中的问题是使搜索非贪婪所必需的。
这是令人惊讶的紧凑和工作的短语,如“甜甜圈”与每个字母的单个实例,但会打破像“咖啡”的字母加倍。 “免费摩卡咖啡”应该与此相匹配吗? – tadman
好点,@tadman。我修正了这一点。 –
这里有两种变体的方法,一种是字母必须按顺序出现,另一种是顺序不相关。在这两种情况下,每封信的频率都受到尊重,所以“咖啡”必须与两个'f'和两个'e'字母匹配,“免费摩卡咖啡”不足以匹配,缺少第二个“f”。
def sorted_string(string)
string.split('').sort.join
end
def phrase_regexp_sequence(phrase)
Regexp.new(
phrase.downcase.split('').join('.*')
)
end
def phrase_regexp_unordered(phrase)
Regexp.new(
phrase.downcase.gsub(/\W/, '').split('').sort.chunk_while(&:==).map do |bit|
"#{bit[0]}{#{bit.length}}"
end.join('.*')
)
end
def contains_unordered(phrase, string)
!!phrase_regexp_unordered(phrase).match(sorted_string(string.downcase))
end
def contains_sequence(phrase, string)
!!phrase_regexp_sequence(phrase).match(string.downcase)
end
strings = [
"I love donuts!",
"Squirrels do love nuts",
"donuts do stun me",
"no stunned matches",
]
phrase = 'donut'
strings.each do |string|
puts '%-30s %s %s' % [
string,
contains_unordered(phrase, string),
contains_sequence(phrase, string)
]
end
# => I love donuts! true true
# => Squirrels do love nuts true true
# => donuts do stun me true true
# => no stunned matches true false
http://*.com/questions/25938430/ruby-count-the-number-of-times-a-string-appears-in-another-string – Zepplock
的可能重复这个问题* *不是**以上的重复,因为这里''眩晕''匹配''甜甜圈'',例如未请求子串匹配。 – mudasobwa
不重复。虽然不同,我在我的帖子上指出这另一个SO:http://*.com/questions/8258517/how-to-check-whether-a-string-contains-a-substring-in-ruby其中“排序“字符串无关紧要。也许“秩序”不是一个好的描述。对困惑感到抱歉!正如@mudasobwa所说,“甜甜圈”和“眩晕”都应该返回匹配。 – Iggy