2014-11-14 69 views
0

我有一個正則表達式來匹配x = y形式的字符串。即名稱分配了一個值。該值可以選擇性地引用和兩個名稱和值符合\ w +正則表達式和分組

我的正則表達式是

\w+=\w+|"\w+"|'\w+' 

可以有多個在同一行這些任務的,但在這裏,我遇到了問題。由於某種原因,當我把這個正則表達式放在(?:)中時,它將不匹配。見測試用例下面

use Test::More; 

my $re1 = qr/^\w+=\w+|"\w+"|'\w+'$/p; 
my $re2 = qr/^(?:\w+=\w+|"\w+"|'\w+')$/p; 

ok('xy="abc"' =~ $re1); 

say "PREMATCH ${^PREMATCH}"; 
say "MATCH ${^MATCH}"; 
say "POSTMATCH ${^POSTMATCH}"; 


ok('xy="abc"' =~ $re2); 

done_testing; 

輸出是

ok 1 
PREMATCH xy= 
MATCH "abc" 
POSTMATCH 
not ok 2 
# Failed test at ./test.pl line 20. 
1..2 
# Looks like you failed 1 test of 2. 

我不明白爲什麼第一場比賽和第二個不行。而且我也不明白爲什麼第一個匹配等號後的部分。

+0

你們是不是要同時匹配'xy'和'「ABC」'? – Degustaf 2014-11-14 19:08:26

回答

1

^\w+=\w+|"\w+"|'\w+'$ 

相當於

(?:^\w+=\w+)|(?:"\w+")|(?:'\w+'$) 

它的^其次是發生在的結束詞或周圍字的單引號周圍的空格或引號匹配串。

^(?:\w+=\w+|"\w+"|'\w+')$ 

要求所有這些基團開始內的線(由於^以外的基團的)的開始,則各種測試,並的那麼所有這些基團都必須在字符串的末尾完成(由於組外的$)。

最簡單的解決方法是簡單的兩個^$進入到組:

(?:^\w+=\w+|"\w+"|'\w+'$) 
+0

是不是'^'只是變化的第一選擇的一部分? – Degustaf 2014-11-14 19:00:58

+0

在$ re1的情況下,'^'是第一個替代選項的一部分。當在$ re2中遇到'(?:...)'組時,'^'被移到了我認爲會導致一些問題的交替之外。 – OnlineCop 2014-11-14 19:03:56

2

您有您的輪換問題。它將第一個管道之前的整個正則表達式部分作爲一個選項。換句話說,

/^\w+=\w+|"\w+"|'\w+'$/ 

被解析成三種可能性,以匹配

^\w+=\w+ 
"\w+" 

'\w+'$ 

爲了解決這個問題,你有兩個選擇(我看到)。首先每個這些選擇擴大到你真正想要的:

/^\w+=\w+|^\w+="\w+"|^\w+='\w+'$/ 

二是集羣交替:

/^\w+=(?:\w+|"\w+"|'\w+')$/