我有一个具有可变长度部分的字符串。该部分的长度在该部分的内容之前。例如,在字符串中:
13JOHNSON,STEVE
前 2 个字符定义内容长度 (13),然后是实际内容。我希望能够使用带有反向引用的命名捕获组来解析它,但我不确定它是否可能。我希望这会奏效:
(?<length>\d{2})(?<name>.{\k<length>})
但事实并非如此。似乎反向引用没有被解释为数字。不过,这很好用:
(?<length>\d{2})(?<name>.{13})
不,那当然行不通。提取第一个数字后,您需要重新编译正则表达式。
我建议您使用两种不同的表达式:第一个提取数字,第二个提取基于第一个提取的数字的文本。
你不能那样做。
>> s = '13JOHNSON,STEVE'
=> "13JOHNSON,STEVE"
>> length = s[/^\d{2}/].to_i # s[0,2].to_i
=> 13
>> s[2,length]
=> "JOHNSON,STEVE"
这真的好像你正在努力追求这个。我怀疑示例字符串并不像你说的那么简单,基于:
我有一个具有可变长度部分的字符串。该部分的长度在该部分的内容之前。
相反,我会使用类似的东西:
str = "13JOHNSON,STEVE 08Blow,Joe 10Smith,John"
str.scan(/\d{2}(\S+)/).flatten # => ["JOHNSON,STEVE", "Blow,Joe", "Smith,John"]
如果字符串可以准确拆分,那么就是这样:
str.split.map{ |s| s[2..-1] } # => ["JOHNSON,STEVE", "Blow,Joe", "Smith,John"]
如果您只有长度字节后跟字符串,它们之间没有任何类似的东西:
offset = 0
str.delete!(' ') # => "13JOHNSON,STEVE08Blow,Joe10Smith,John"
str.scan(/\d+/).map{ |l| s = str[offset + 2, l.to_i]; offset += 2 + l.to_i ; s }
# => ["JOHNSON,STEVE", "Blow,Joe", "Smith,John"]
如果名称中包含数字,则无法使用 – tihom
str = "13JOHNSON,STEVE 08Blow,Joe 10Smith,John 1012345,7890"
str.scan(/\d{2}(\S+)/).flatten # => ["JOHNSON,STEVE", "Blow,Joe", "Smith,John", "12345,7890"]
str.split.map{ |s| s[2..-1] } # => ["JOHNSON,STEVE", "Blow,Joe", "Smith,John", "12345,7890"]
通过一个小的更改和小的添加,它将继续与不包含分隔符的字符串一起正常工作:
str.delete!(' ') # => "13JOHNSON,STEVE08Blow,Joe10Smith,John1012345,7890"
offset = 0
str.scan(/\d{2}/).map{ |l| s = str[offset + 2, l.to_i]; offset += 2 + l.to_i ; s }.compact
# => ["JOHNSON,STEVE", "Blow,Joe", "Smith,John", "12345,7890"]
\d{2}
抓取两个一组的数字。对于数字是两个字符的前导长度值的名称,根据 OPs 示例,会发生正确的事情。对于一个实心数字“名称”,会返回几个误报,这将返回nil
值。compact
清除那些。
那这个呢?
a = '13JOHNSON,STEVE'
puts a.match /(?<length>\d{2})(?<name>(.*),(.*))/