Tengo un archivo de texto extenso; a continuación se muestra parte del contenido del archivo.
[{"site":"1a2v_1","pfam":"Cu_amine_oxid","uniprot":"P12807"},{"site":"1a2v_2","pfam":"Cu_amine_oxid","uniprot":"P12807"},{"site":"1a2v_3","pfam":"Cu_amine_oxid","uniprot":"T12807"},{"site":"1a2v_4","pfam":"Cu_amine_oxid","uniprot":"P12808"},{"site":"1a2v_5","pfam":"Cu_amine_oxid","uniprot":"Z12809"},{"site":"1a2v_6","pfam":"Cu_amine_oxid","uniprot":"P12821"},{"site":"1a3z_1","pfam":"Copper-bind,SoxE","uniprot":"P0C918"},
Necesito analizar uniprot
los identificadores del archivo de texto anterior y el resultado esperado se proporciona a continuación:
P12807
P12807
T12807
P12808
Z12809
P12821
P0C918
Para hacer lo mismo, probé los siguientes comandos pero nada me funciona,
sed -e 's/"uniprot":"\(.*\)"},{"site":"/\1/' file.txt
cat file.txt | sed 's/.*"uniprot":" //' | sed 's/"site":".*$//'
Por favor ayúdenme a analizar los identificadores como se mencionó anteriormente.
Gracias de antemano.
Respuesta1
Si estás en un sistema Linux, puedes hacer muy fácilmente:
$ grep -oP '"uniprot":"\K[^"]+' file
P12807
P12807
T12807
P12808
Z12809
P12821
P0C918
Le -o
indica grep
que solo se imprima la parte coincidente de cada línea y -P
habilita las expresiones regulares compatibles con Perl. La expresión regular está buscando "uniprot":"
pero luego la descarta (lo \K
que significa "descartar todo lo que coincida hasta ahora", para que no se incluya en la salida). Luego, simplemente busca el tramo más largo de no "
( [^"]+
).
Por supuesto, esto parece datos JSON, por lo que para cualquier cosa más complicada, debe usar un analizador adecuado como jq
. Si arregla su archivo agregando un cierre ]
y lo hace así:
[{"site":"1a2v_1","pfam":"Cu_amine_oxid","uniprot":"P12807"},{"site":"1a2v_2","pfam":"Cu_amine_oxid","uniprot":"P12807"},{"site":"1a2v_3","pfam":"Cu_amine_oxid","uniprot":"T12807"},{"site":"1a2v_4","pfam":"Cu_amine_oxid","uniprot":"P12808"},{"site":"1a2v_5","pfam":"Cu_amine_oxid","uniprot":"Z12809"},{"site":"1a2v_6","pfam":"Cu_amine_oxid","uniprot":"P12821"},{"site":"1a3z_1","pfam":"Copper-bind,SoxE","uniprot":"P0C918"}]
Tu puedes hacer:
$ jq -r '.[].uniprot' file
P12807
P12807
T12807
P12808
Z12809
P12821
P0C918
Respuesta2
Si observa con atención, su archivo de entrada es una estructura de datos de Python. En particular, es una lista de diccionarios. Necesitamos agregar un corchete de cierre.
Mediante el módulo ast podemos serializar la cadena que es una estructura de datos válida de Python.
python3 -c 'import sys, ast
ifile,key = sys.argv[1:]
str = ""
with open(ifile) as fh:
for l in fh: str += l.rstrip()
lod = ast.literal_eval(str)
for d in lod: print(d[key])
' file uniprot
P12807
P12807
T12807
P12808
Z12809
P12821
P0C918
Respuesta3
Usando gawk
:
awk 'BEGIN{RS=","}
/uniprot/{print gensub(/.*("uniprot":")(.*)".*/, "\\2", "g") }' input
En este comando, la entrada Separador de registros ( RS
) se establece en coma.
Luego, gawk
la función incorporada gensub()
reemplaza la línea con el patrón deseado usando referencias inversas ( \\2
).
Respuesta4
solución Perl 5
$ perl -nle 'print join"\n",m/uniprot\":\"(.*?)\"/g' file.txt
P12807
P12807
T12807
P12808
Z12809
P12821
P0C918
$