2009-05-22 20 views
3

Okay, also habe ich ein halbwerdisches Problem mit re.Regulärer Ausdruck Subprobleme

Nehmen Sie den folgenden Code ein:

import re 
str_to_be_subbed = r'somefile.exe -i <INPUT>' 
some_str = r'C:\foobar' 
s = re.sub(r'\<INPUT\>', some_str, str_to_be_subbed) 
print s 

Ich denke, es wäre würde mir geben:

somefile.exe -i C:\\foobar 

Aber anstatt es gibt mir:

somefile.exe -i C:♀oobar 

Ich weiß, \ f ein Escape char, aber auch wenn ich versuche es so zu machen, was den speziellen Charakteren entgehen sollte. Auch wenn ich dies tun:

print r'%s' % s 

Es gibt mir immer noch so:

somefile.exe -i C:♀oobar 

Warum es dies tut? Und was ist der beste Weg, dies zu vermeiden?

Ninja Edit:

Wenn i auf den Wert von s aussehen es ist:

'somefile.exe -i C:\x0coobar' 

Warum \ f wiederum in \ x0 tat. Pfui.

Edit:

Noch eine Frage, wenn ich den Code auf diese ändern:

import re 
import os 
str_to_be_subbed = r'somefile.exe -i <INPUT>' 
some_str = os.path.abspath(r'C:\foobar') 
some_str 
s = re.sub(r'\<INPUT\>', some_str, str_to_be_subbed) 
print s 

Gibt mir:

>>> import re 
>>> import os 
>>> str_to_be_subbed = r'somefile.exe -i <INPUT>' 
>>> some_str = os.path.abspath(r'C:\foobar') 
>>> some_str 
'C:\\foobar' 
>>> s = re.sub(r'\<INPUT\>', some_str, str_to_be_subbed) 
>>> print s 
somefile.exe -i C:♀oobar 

Nun, warum das so ist. Seit os.path.abspath entkommt der \ 's. Warum versagt re noch?

Auch dies ist ein wirklich kleines Beispiel dieses kleinen Problems, das zufällig in einer alten Anwendung auftaucht. Ich kann nicht wirklich gehen und dies zu string.replace wegen seiner Einrichtung ändern, ohne einen ganzen Tag zu verbringen.

Ich bin nur wirklich neugierig, warum es das tut. Für das obige Problem.

Antwort

3

\f ist die Form Feed Zeichen. Entfliehen Sie es und es funktioniert:

some_str = r'C:\\foobar' 

Eine andere Lösung:

s = re.sub(r'<INPUT>', some_str.encode("string_escape"), str_to_be_subbed) 
+0

Danke. Encode funktioniert erstaunlich. – UberJumper

3

Verwenden Sie keine regulären Ausdrücke:

print str_to_be_subbed.replace("<INPUT>",some_str) 

Als documentation sagt:

repl können Sei eine Zeichenfolge oder eine Funktion; Wenn es eine Zeichenfolge ist, wird jeder umgekehrte Schrägstrich darin verarbeitet.

+0

Ich kann String ersetzen nicht verwenden. Ich muss die Regex-Formular verwenden, sonst werde ich gezwungen, Hunderte von Zeilen von jemandes Code zu ändern/zu ändern. – UberJumper

0

Ihr Beispiel nicht regexps benötigt, verwenden str.replace():

>>> str_to_be_subbed.replace('<INPUT>',some_str) 
'somefile.exe -i C:\\foobar' 
>>> 
2

Python docs sagen ...

re.sub (Muster, repl, string, count = 0, flags = 0) Die zurückgegebene Zeichenfolge zurückgeben, indem das nicht überlappende Vorkommen des Musters ganz links in Zeichenfolge durch das Ersatz-Replikat ersetzt wird. Wenn das Muster nicht gefunden wird, wird die Zeichenfolge unverändert zurückgegeben. repl kann eine Zeichenfolge oder eine Funktion sein; Wenn es sich um eine Zeichenfolge handelt, werden alle Backslash-Escapes in ihm verarbeitet. Das heißt, \ n wird in ein einzelnes Zeilenumbruchzeichen umgewandelt, \ r wird in einen Wagenrücklauf konvertiert und so weiter. Unbekannte Escapes wie \ j sind alleine gelassen

Deshalb gibt es "C: ♀oobar".

Wenn wir jedoch eine Funktion als zweites Argument angeben, werden keine umgekehrten Schrägstriche konvertiert.

So versuchen folgende ..

>>>import re 
>>>str_to_be_subbed = r'somefile.exe -i <INPUT>' 
>>>some_str = r'C:\foobar' 
>>>s = re.sub(r'\<INPUT\>', lambda _:some_str, str_to_be_subbed) 
>>>print s 
somefile.exe -i c:\foobar