2016-08-24 126 views
1

我正在尋找提取包含版本號的數組元素,其中版本號是在字符串的開始或結尾或由空格填充,並且是一系列數字和句點,但不以句號開始或結束。例如「10.10 Thingy」和「Thingy 10.10.5」是有效的,但「無論4」不是。使用正則表達式檢測版本號的具體格式

haystack = ["10.10 Thingy", "Thingy 10.10.5", "Whatever 4", "Whatever 4.x"] 
haystack.select{ |i| i[/(?<=^|)(\d+)(\.\d+)*(?=$|)/] } 
=> ["10.10 Thingy", "Thingy 10.10.5", "Whatever 4"] 

我不知道如何修改正則表達式來至少需要一個週期,使得「無論4」的結果是沒有的。

回答

2

這只是Archonic的答案的一個輕微變體。

r =/
    (?<=\A|\s) # match the beginning of the string or a space in a positive lookbehind 
    (?:\d+\.)+ # match >= 1 digits followed by a period in a non-capture group, >= 1 times 
    \d+  # match >= 1 digits 
    (?=\s|\z) # match a space or the end of the string in a positive lookahead 
    /x   # free-spacing regex definition mode 

haystack = ["10.10 Thingy", "Thingy 10.10.5", "Whatever 4", "Whatever 4.x"] 

haystack.select { |str| str =~ r } 
    #=> ["10.10 Thingy", "Thingy 10.10.5"] 

問題不在於返回版本信息,而是爲了返回具有正確版本信息的字符串。其結果是沒有必要的lookarounds:

r =/
    [\A\s\] # match the beginning of the string or a space 
    (?:\d+\.)+ # match >= 1 digits followed by a period in a non-capture group, >= 1 times 
    \d+  # match >= 1 digits 
    [\s\z]  # match a space or the end of the string in a positive lookahead 
    /x   # free-spacing regex definition mode 

haystack.select { |str| str =~ r } 
    #=> ["10.10 Thingy", "Thingy 10.10.5"] 

假設有人想同時獲得包含有效的版本字符串和包含在這些字符串的版本。可以寫下面的內容:

r =/
    (?<=\A|\s\) # match the beginning of string or a space in a pos lookbehind 
    (?:\d+\.)+ # match >= 1 digits then a period in non-capture group, >= 1 times 
    \d+   # match >= 1 digits 
    (?=\s|\z) # match a space or end of string in a pos lookahead 
    /x   # free-spacing regex definition mode 

haystack.each_with_object({}) do |str,h| 
    version = str[r] 
    h[str] = version if version 
end 
    # => {"10.10 Thingy"=>"10.10", "Thingy 10.10.5"=>"10.10.5"} 
+0

感謝您的詳細信息! – Archonic

1

啊哈!我知道我很親密。

haystack.select{ |i| i[/(?<=^|)(\d+)(\.\d+)+(?=$|)/] }

(\.\d+)*末尾的星號被允許該圖案以重複任何次數,包括零次。你可以用(\.\d+){x,y}來限制它,其中x和y是最小和最大時間。您也只能通過(\.\d+){x,}來確定最小值。在我的情況下,我想要至少一次,這將是(\.\d+){1,},但這是(\.\d+)+的代名詞。這隻花了一天的時間才能發現......