我正在使用Rails 4.2.7(Ruby 2.3)。我使用以下内容基于正则表达式分割字符串
my_string.split(/\W+/)
我的问题是,如何获得一个等价数组,其中每个数字代表分裂发生位置的索引?如果没有发生拆分,我希望数组只包含一个带“-1”的元素。
答案 0 :(得分:1)
所以,你不想分裂,你只想要指数吗?
a = []
"Hello stack overflow".scan(/\W+/){a<<Regexp.last_match.begin(0)}
a
#=> [5, 11]
空数组意味着不会发生拆分。
编辑:更短的版本可能是
"Hello stack overflow".enum_for(:scan, /\W+/).map{Regexp.last_match.begin(0)}
#=> [5, 11]
答案 1 :(得分:0)
在某些情况下,String#split会在具有多个字符的子字符串上拆分字符串。每个子字符串开头的字符串偏移量可能不足。可能需要开始和结束指数。
以下方法返回元组数组,每个元组的第一个元素是strip
返回的字符串部分,第二个元素是子字符串开始的索引。请注意,这只提供了计算所需索引的方法,但它也返回split
返回的子字符串。
def split_with_offsets(str, r)
indices = []
str.scan(r) { indices << Regexp.last_match.begin(0) }
str.split(r).zip(indices << str.size).map { |s,ndx| [s, ndx-s.size] }
end
使用此信息可以直接获得范围数组,每个范围都是分割条带的子字符串的偏移量。
def gaps(str, r)
split_with_offsets(str, r).each_cons(2).map { |(s,f), (_,lp1)| f+s.size..lp1-1 }
end
以下是两个例子。
#1
str = "Hello stack overflow"
r = /\W+/
split_with_offsets(str, r)
#=> [["Hello", 0], ["stack", 6], ["overflow", 12]]
gaps(str, r)
#=> [5..5, 11..11]
#2
str = "I | cannot | wait | for | the election |to |be | over"
r = /\s*\|\s*/
split_with_offsets(str, r)
#=> [["I", 0], ["cannot", 4], ["wait", 13], ["for", 20], ["the election", 29],
# ["to", 43], ["be", 47], ["over", 53]]
gaps(str, r)
#=> [1..3, 10..12, 17..19, 23..28, 41..42, 45..46, 49..52]