2013-03-31 37 views
1

我想下面的字符串解碼:Ruby的正則表達式前瞻在管道內來分割

body = '{type:paragaph|class:red|content:[class:intro|body:This is the introduction paragraph.][body:This is the second paragraph.]}' 
body << '{type:image|class:grid|content:[id:1|title:image1][id:2|title:image2][id:3|title:image3]}' 

我需要串在管道拆分而不是其中一個管被包含同方括號,要做到這一點,我想我需要執行一個超前如下所述:How to split string by ',' unless ',' is within brackets using Regex?

我嘗試(仍然分裂在每個管):

x = self.body.scan(/\{(.*?)\}/).map {|m| m[0].split(/ *\|(?!\]) */)} 
-> 
[ 
    ["type:paragaph", "class:red", "content:[class:intro", "body:This is the introduction paragraph.][body:This is the second paragraph.]"] 
    ["type:image", "class:grid", "content:[id:1", "title:image1][id:2", "title:image2][id:3", "title:image3]"] 
] 

Expectin G:

-> 
    [ 
     ["type:paragaph", "class:red", "content:[class:intro|body:This is the introduction paragraph.][body:This is the second paragraph.]"] 
     ["type:image", "class:grid", "content:[id:1|title:image1][id:2|title:image2][id:3|title:image3]"] 
    ] 

有誰知道這裏所需要的正則表達式?

是否有可能匹配這個正則表達式?我似乎無法正確地修改它Regular Expression to match underscores not surrounded by brackets?


我修改的答案在這裏Split string in Ruby, ignoring contents of parentheses?獲得:

self.body.scan(/\{(.*?)\}/).map {|m| m[0].split(/\|\s*(?=[^\[\]]*(?:\[|$))/)} 

似乎這樣的伎倆。雖然我確定是否有任何不足之處。

+0

您嘗試按管道拆分,但不包含一個,只能向前看一個字符,所以沒有看到管道。如果你把它放在更前面,你還需要聲明沒有開放支架。您還需要斷言沒有以前的開頭括號。在這個階段,值得考慮以不同的方式收集解析結構。 。 。 –

+0

括號是否出現在封裝輸入字符串位的上下文中?也就是'this | [是一個字符串] |使用孤兒]的值嗎? –

+0

不,它們只用於上述情況。 –

回答

1

我修改的答案在這裏Split string in Ruby, ignoring contents of parentheses?獲得:

self.body.scan(/\{(.*?)\}/).map {|m| m[0].split(/\|\s*(?=[^\[\]]*(?:\[|$))/)} 

似乎這樣的伎倆。如果有任何不足之處,請提供更好的建議。

+0

如果在你的結構中沒有更深的'{}'或'[]'嵌套,我認爲它會好的。你仍然沒有完成解析數據,除非你能夠按原樣使用結果。下一步,我猜想是將每個項目分割在':'(僅限第一個項目)之後,然後檢測嵌入式列表並重復您的想法,但使用像'scan(/\[(.*?)\]/) '。 。 。 –

+0

這就是我所擁有的。謝謝你的幫助。 –

3

處理具有相同語法的嵌套結構會給你帶來困難。

你可以嘗試一個遞歸下降解析器(快速谷歌打開了https://github.com/Ragmaanir/grammy - 不知道什麼好)

就個人而言,我會去真正哈克的東西 - 一些gsubs是將您的字符串轉換成JSON,然後使用JSON解析器解析:-)。這並不是特別容易的事,不過,但這裏有雲:

require 'json' 

b1 = body.gsub(/([^\[\|\]\:\}\{]+)/,'"\1"').gsub(':[',':[{').gsub('][','},{').gsub(']','}]').gsub('}{','},{').gsub('|',',') 


JSON.parse('[' + b1 + ']') 

這並不容易,因爲字符串格式顯然使用[foo:bar][baz:bam]代表散列的數組。如果您有機會修改序列化格式以使其更容易,我會接受它。

+0

你能推薦更好的sting格式來達到同樣的效果嗎?字符串的格式很靈活。目標是擁有一個散列數組,內容散列也用於包含另一個散列數組。 –

+0

是否可以使用JSON?它比你的格式略爲冗長,但它可以輕鬆地對需要的結構進行序列化和反序列化,並且解析器已經可以用多種語言提供。 –

+0

我修改了答案在這裏http://stackoverflow.com/questions/2015826/split-string-in-ruby-ignoring-contents-of-parentheses得到'self.body.scan(/\{(.*?) \} /)。map {| m | m [0] .split(/ \ | \ s *(?= [^ \ [\]] *(?:\ [| $))/)}'似乎可以做到這一點。 –