2013-11-14 67 views
3

我正在使用Ruby的StringScanner來標準化一些英文文本。如何從StringScanner捕獲項目?

def normalize text 
    s = '' 
    ss = StringScanner.new text 
    while ! ss.eos? do 
    s += ' ' if ss.scan(/\s+/)    # mutiple whitespace => single space 
    s += 'mice' if ss.scan(/\bmouses\b/) # mouses => mice 
    s += '' if ss.scan(/\bthe\b/)   # remove 'the' 
    s += "#$1 #$2" if ss.scan(/(\d)(\w+)/) # should split 3blind => 3 blind 
    end 
    s 
end 

normalize("3blind the mouses") #=> should return "3 blind mice" 

相反,我只是得到" mice"

StringScanner#scan未捕獲(\d)(\w+)

回答

4

要訪問StringScanner捕獲(Ruby的1.9及以上),您可以使用StringScanner#[]

s += "#{ss[1]} #{ss[2]}" if ss.scan(/(\d)(\w+)/) # splits 3blind => 3 blind 

在Ruby 2.1,你應該能夠通過名字來捕獲(見彼得Alfvin的link

s += "#{ss[:num]} #{ss[:word]}" if ss.scan(/(?<num>\d)(?<word>\w+)/) 
+0

回到你身邊! :-)不能相信我錯過了。 –

+0

是的,在ruby文檔中很難看到''[]''。 – zhon

2

注意:這個/我的答案的第一個版本是完全離開基地,每個評論線程。道歉。

基於對http://ruby-doc.org/stdlib-1.9.2/libdoc/strscan/rdoc/StringScanner.html試驗和審查,看來StringScanner沒有設置匹配變量$1$2,等等,這樣最後s += ...語句僅追加一個空白以s

看着strscan.c看來,確實有用於提供捕獲匹配信息的支持,但我沒有找到https://www.ruby-forum.com/topic/4413436,這似乎是一個正在進行的努力某種實現這個

+0

當我調用''normalize''以避免混淆時更改。 – zhon

+0

其實,[scan pointer](http://www.ruby-doc.org/stdlib-2.0.0/libdoc/strscan/rdoc/StringScanner.html)不會移動,直到''scan''返回除了''nil''(我沒有使用任何其他方法來提前掃描指針)。因此,它可以「掃描」的第一件事是「3blind」。爲了簡化問題,我省略了「下一個」。 – zhon

+0

確實。正在處理中,請稍候...... :-) –