2011-03-16 61 views
10

python新增功能。這可能很簡單,但我還沒有找到答案。如何在Python中使用匹配的組和變量進行分組

rndStr = "20101215" 
rndStr2 = "20101216" 
str = "Looking at dates between 20110316 and 20110317" 
outstr = re.sub("(.+)([0-9]{8})(.+)([0-9]{8})",r'\1'+rndStr+r'\2'+rndStr2,str) 

我在尋找的輸出是:

Looking at dates between 20101215 and 20101216 

而是我得到:

P101215101216 

兩個rndStr的其實並不重要的價值。假設它的隨機或從用戶輸入(我把靜態vals在這裏保持簡單)。謝謝你的幫助。

回答

21

您的反向引用不明確。你替換字符串變成

\120101215\220101216 

這是兩個相當大的數字被逆向引用:)

爲了解決這個問題,使用此語法:

r'\g<1>'+rndStr+r'\g<2>'+rndStr2 

也有太多的套括號(或「括號」,如果你像我一樣說英式英語:) - 你不需要括號圍繞[0-9]{8}部分,你不是反向參考:

re.sub("(.+)[0-9]{8}(.+)[0-9]{8}",... 

應該足夠。 (並且,如其他地方所述,不要使用str作爲變量名稱,除非您想花費年齡調試爲什麼str.replace()不再有效,不是我曾經這麼做過一次......沒有。:)

所以整個事情變成:

import re 
rndStr = "20101215" 
rndStr2 = "20101216" 
s = "Looking at dates between 20110316 and 20110317" 
outstr = re.sub("(.+)[0-9]{8}(.+)[0-9]{8}", r'\g<1>'+rndStr+r'\g<2>'+rndStr2, s) 
print outstr 

生產:

Looking at dates between 20101215 and 20101216 
-1
rndStr = "20101215" 
rndStr2 = "20101216" 
mys = "Looking at dates between {0} and {1}".format(rndStr, rndStr2) 

請不要使用str作爲變量名;它會覆蓋內置的str類型。

+1

我不認爲OP要求這樣做。 – 2011-03-16 22:13:15

+0

原始字符串有兩個(不同)日期,所以這不會工作。不管怎麼說,還是要謝謝你。 – 2011-03-17 14:42:58

3

注意,如果你改變的rndStr或01的值到文本(比如'abc')而不是數字,你會得到更接近預期結果的東西嗎?

在你表達re.sub你有r'\1'+rndStr+...這組合成'\1'+'20101215',然後嘗試引用的\120101215後面參考這可能不是你打算什麼...

可以使用指定的反向引用,使回參考明確:

rep1 = "20101215" 
rep2 = "20101216" 
st = "Looking at dates between 20110316 and 20110317" 

print re.sub(r'(?P<fp>.+)[0-9]{8}(?P<lp>.+)[0-9]{8}', 
      r'\g<fp>'+rep1+r'\g<lp>'+rep2,st) 

更妙的是,使用一個更容易理解的語法和檢查嘗試匹配的回報:

m=re.search(r'(?P<fp>.+)[0-9]{8}(?P<lp>.+)[0-9]{8}',st) 
if m: 
    print m.group('fp')+rep1+m.group('lp')+rep2 #you could use m.group(1) too 
else: 
    print "no match..." 

無論哪種情況,都會生成您想要的字符串Looking at dates between 20101215 and 20101216

命名後向引用python的docs:

(?P<name>...)

定期括號相似,但 由組相匹配的字符串是通過符號 的 正則表達式的其餘部分中訪問組名「name」。組名必須爲 有效的Python標識符,並且每個 組名必須在正則表達式中僅定義一次 。 A 符號組也是一個編號爲 的組,就好像該組不是 命名。因此,在下面的例子 名爲'id'的組也可被引用作爲 編號組1

例如,如果圖案是 (?P<id>[a-zA-Z_]\w*),該基團可以是 通過其名稱在參數參照的 方法匹配的對象,如 m.group('id')m.end('id'),並且還通過 名稱在給予.sub()正則表達式 本身(使用(?P=id))和替換 文本(使用\g<id>)。

+0

謝謝 - 希望我可以分配兩個正確的答案:-) – 2011-03-17 14:40:50

+0

@Syed H:所有的事情都是平等的,你應該選擇第一個正確的答案恕我直言,這就是你所做的。我添加了我的答案,只是作爲替代...感謝您的評論。 – dawg 2011-03-17 15:41:35

-1
rndStr = "20101215" 
rndStr2 = "20101216" 

print "Looking at dates between %s and %s" %(rndStr,rndStr2) 
+1

同樣在這裏,原始字符串有兩個(不同的)日期,所以這不會工作。不管怎麼說,還是要謝謝你。 – 2011-03-17 14:43:38

相關問題