Escaping dei caratteri speciali nelle espressioni regolari di Python
Supponiamo di voler fare in modo che un carattere speciale rappresenti se stesso. A questo scopo è necessario escaparlo utilizzando la barra rovesciata. Vediamo alcuni esempi.
Esempio
Nell'esempio seguente, l'autore dell'espressione regolare voleva
che il modello di ricerca fosse il seguente: lettera
'a', poi il segno più '+', poi
lettera 'x'. Tuttavia, l'autore del codice
non ha escapato il carattere '+' e quindi
il modello di ricerca in realtà è questo:
lettera 'a' una o più volte,
poi lettera 'x':
txt = 'a+x ax aax aaax'
res = re.sub('a+x', '!', txt)
print(res)
Risultato dell'esecuzione del codice:
'a+x ! ! !'
Esempio
Ora l'autore ha escapato il segno più con la barra rovesciata.
Ora il modello di ricerca è come dovrebbe essere:
lettera 'a', poi segno più
'+', poi lettera 'x':
txt = 'a+x ax aax aaax'
res = re.sub('a\+x', '!', txt)
print(res)
Risultato dell'esecuzione del codice:
'! ax aax aaax'
Esempio
In questo esempio, il modello è il seguente:
lettera 'a', poi punto '.',
poi lettera 'x':
txt = 'a.x abx azx'
res = re.sub('a\.x', '!', txt)
print(res)
Risultato dell'esecuzione del codice:
'! abx azx'
Esempio
Nel prossimo esempio l'autore si è dimenticato di escapare il punto e la regex ha catturato tutte le sottostringhe, poiché un punto non escapato rappresenta qualsiasi carattere:
txt = 'a.x abx azx'
res = re.sub('a.x', '!', txt)
print(res)
Risultato dell'esecuzione del codice:
'! ! !'
Osservazione
Nota che se dimentichi la barra rovesciata per il punto (quando dovrebbe rappresentare se stesso) - potrebbe persino passare inosservato:
res = re.sub('a.x', '!', 'a.x')
print(res) # restituirà '!', come volevamo
Visivamente funziona correttamente (poiché il punto
rappresenta qualsiasi carattere, incluso un
punto normale '.'). Ma se cambiamo
la stringa in cui avvengono le sostituzioni -
vedremo il nostro errore:
res = re.sub('a.x', '!', 'a.x abx azx')
print(res) # restituirà '! ! !', ma ci si aspettava '! abx azx'
Lista dei caratteri speciali e ordinari
Se si escapa un carattere ordinario - non succede nulla di grave - rappresenterà comunque se stesso. Un'eccezione sono le cifre, non possono essere escapate.
Spesso sorge il dubbio se un determinato carattere sia speciale. Alcuni arrivano al punto di escapare tutti i caratteri sospetti indiscriminatamente. Tuttavia, questa è una cattiva pratica (ingombra la regex con barre rovesciate).
Sono caratteri speciali: $ ^ . * + ? \ / {} [] () |
Non sono caratteri speciali: @ : , ' " - _ = < > % # ~ `& !
Problemi pratici
Data la stringa:
txt = 'a.a aba aea'
Scrivi un'espressione regolare che trovi la stringa
'a.a', senza catturare le altre.
Data la stringa:
txt = '2+3 223 2223'
Scrivi un'espressione regolare che trovi la stringa
'2+3', senza catturare le altre.
Data la stringa:
txt = '23 2+3 2++3 2+++3 345 567'
Scrivi un'espressione regolare che trovi le stringhe
'2+3', '2++3', '2+++3',
senza catturare le altre (+ può essere qualsiasi
numero).
Data la stringa:
txt = '23 2+3 2++3 2+++3 445 677'
Scrivi un'espressione regolare che trovi le stringhe
'23', '2+3', '2++3',
'2+++3', senza catturare le altre.
Data la stringa:
txt = '*+ *q+ *qq+ *qqq+ *qqq qqq+'
Scrivi un'espressione regolare che trovi le stringhe
'*q+', '*qq+', '*qqq+',
senza catturare le altre.
Data la stringa:
txt = '[abc] {abc} abc (abc) [abc]'
Scrivi un'espressione regolare che trovi le stringhe
tra parentesi quadre e le sostituisca con
'!'.