2014-06-11 37 views
1

我想提取一個函數的第一個和第二個參數(如果有的話)。我想提取param1param2如何提取棘手字符串中的參數

這裏是我發現貓膩:

  1. 可能沒有第二個參數
  2. 參數報價可能是簡單或雙引號
  3. 雙引號參數可以包含一個單引號,反之亦然。

有些地方要提取參數的可能情況:

__('My test') 
__('Uber test', 'dan') 
__("test t'fdgfgd") 
__("test t'dfgdgf","fgf', 'dgfdg") 

這是what I have tried

+0

解析的編程語言與正則表達式是在多數情況下是沒有希望的企業。考慮一個合適的解析器(例如https://github.com/nikic/PHP-Parser)。 – georg

回答

1

沒錯這是一個有點棘手,但這個工程(見demo與所有你的例子):

(?:__\(|\G['"]\s*,\s*)(['"])\K.*?(?=(?<!\\)\1) 

@NiettheDarkAbsol提到躲過行情的可能性,所以我加了這樣棘手的字符串的條件如:

__('My \'test') 
__("My \"test") 

這是如何工作的?

這是一個有點長令牌通過令牌的解釋,但是......

  1. 這部分(?:__\(|\G['"]\s*,\s*)(['"])\K位置我們開引號內,放棄什麼迄今感謝「博士匹配。\K eep out「。稍後再回來。
  2. .*?懶洋洋地匹配字符,直到達到...
  3. 其中先行(?=(?<!\\)\1)可以斷言,接下來是相同的字符作爲開引號(在\1反向引用)的點,只要不被前面轉義反斜槓((?<!\\)
  4. 好的,第1部分是如何工作的?在「Dr. \K終止」之前,我們或者匹配開頭的__\(,然後打開字符串,由(['"])捕獲以確保結尾字符串相同(稍後參考\1)...或...
  5. 斷言與\G相比,我們在前一場比賽的最後一個字符之後定位,['"]\s*,\s*匹配它的結束報價,然後是逗號(由可選空格包圍),然後是開頭字符串,由(['"])捕獲以確保結尾字符串相同(\1稍後參考)。

而這就是它!

+0

這個句柄如何處理轉義引號? –

+0

@NiettheDarkAbsol你說得對,雖然這不是規範,但這是一個重要的案例。完成。謝謝! :) – zx81

0

這裏是一個正則表達式,會給你匹配:

(?:(?:')((?:(?!(?<!\\)').)+)(?:'(?:,\s*)?))|(?:(?:")((?:(?!(?<!\\)").)+)(?:"(?:,\s*)?)) 

Demo

相關問題