Abbinare regex multilinea in oggetto file
Domanda
Come posso estrarre i gruppi di questa regex da un oggetto file (data.txt)?
import numpy as np
import re
import os
ifile = open("data.txt",'r')
# Regex pattern
pattern = re.compile(r"""
^Time:(\d{2}:\d{2}:\d{2}) # Time: 12:34:56 at beginning of line
\r{2} # Two carriage return
\D+ # 1 or more non-digits
storeU=(\d+\.\d+)
\s
uIx=(\d+)
\s
storeI=(-?\d+.\d+)
\s
iIx=(\d+)
\s
avgCI=(-?\d+.\d+)
""", re.VERBOSE | re.MULTILINE)
time = [];
for line in ifile:
match = re.search(pattern, line)
if match:
time.append(match.group(1))
Il problema nell'ultima parte del codice, è che io iterare riga per riga, che ovviamente non funziona con espressioni regolari multilinea. Ho cercato di usare pattern.finditer(ifile)
in questo modo:
for match in pattern.finditer(ifile):
print match
... solo per vedere se funziona, ma il metodo finditer richiede una stringa o di buffer.
Inoltre ho provato questo metodo, ma non riesco a farlo funzionare
matches = [m.groups() for m in pattern.finditer(ifile)]
Qualche idea?
Dopo commento da Mike e Tuomas, mi è stato detto di usare .read () .. Qualcosa di simile a questo:
ifile = open("data.txt",'r').read()
Questo funziona bene, ma questo sarebbe il modo corretto per la ricerca in file? Non può farlo funzionare ...
for i in pattern.finditer(ifile):
match = re.search(pattern, i)
if match:
time.append(match.group(1))
Soluzione
# Open file as file object and read to string
ifile = open("data.txt",'r')
# Read file object to string
text = ifile.read()
# Close file object
ifile.close()
# Regex pattern
pattern_meas = re.compile(r"""
^Time:(\d{2}:\d{2}:\d{2}) # Time: 12:34:56 at beginning of line
\n{2} # Two newlines
\D+ # 1 or more non-digits
storeU=(\d+\.\d+) # Decimal-number
\s
uIx=(\d+) # Fetch uIx-variable
\s
storeI=(-?\d+.\d+) # Fetch storeI-variable
\s
iIx=(\d+) # Fetch iIx-variable
\s
avgCI=(-?\d+.\d+) # Fetch avgCI-variable
""", re.VERBOSE | re.MULTILINE)
file_times = open("output_times.txt","w")
for match in pattern_meas.finditer(text):
output = "%s,\t%s,\t\t%s,\t%s,\t\t%s,\t%s\n" % (match.group(1), match.group(2), match.group(3), match.group(4), match.group(5), match.group(6))
file_times.write(output)
file_times.close()
Forse può essere scritto più compatto e divinatorio però ....
Soluzione
È possibile leggere i dati dal file oggetto in una stringa con ifile.read()
Altri suggerimenti
Perché non leggere l'intero file in un buffer utilizzando
buffer = open("data.txt").read()
e poi fare una ricerca con questo?
times = [match.group(1) for match in pattern.finditer(ifile.read())]
finditer
resa MatchObjects
. Se l'espressione regolare non corrisponde a nulla times
sarà una lista vuota.
È anche possibile modificare la regex per utilizzare i gruppi non-cattura per storeU
, storeI
, iIx
e avgCI
, volte poi pattern.findall
conterrà solo abbinati.
Nota: denominazione time
variabile potrebbe ombra modulo di libreria standard. times
sarebbe una scelta migliore.