Procesar texto con head, tail, cat, split…

Este es uno de los capítulos del tutorial El terminal. Encontrarás los enlaces a todos los de capítulos, al final de este artículo.

Siguiendo con el capítulo anterior de este tutorial, que trataba de filtros, en este nuevo capítulo te indicaré mas herramientas. Se trata todo de herramientas orientadas a trabajar con archivos y procesar te texto, que te van a permitir modificar el contenido con muy poco esfuerzo. El único esfuerzo que debes hacer es ahora, conocer estas herramientas y empezar a utilizarlas.

Algunas de las herramientas que verás en este capítulo del tutorial, seguro te serán de gran utilidad para mas que modificar archivos de texto. Así puedes, revisar logs, encadenar procesos y mas.

El problema de este capítulo del tutorial, como del anterior, es que si no lo utilizas, te pasará como te sucede con el inglés. Lo olvidarás. Sin embargo, solo tienes que recordar donde lo viste una vez, aquí.

Mas filtros: procesar texto con head, tail, cat, split...

Filtros. Procesar texto

head

Este primera utilidad o herramienta para procesar texto, te permite extraer las primeras n líneas de un archivo. El uso es tan sencillo como,

head [opciones] archivo

De entre las opciones disponibles quiero destacar,

  • -n. Con esta opción indicas el número de líneas que quieres extraer. Así si indicas head -n 4 el_quijote.txt extraerás las 4 primeras líneas.
  • -c bytes. En este caso en lugar de líneas se refiere a bytes o caracteres, dada que un carácter se corresponde con un byte. Así si ejecutas head -c 4 el_quijote.txt sacarás los cuatro primeros caracteres. Pero y si quisieras sacar los primeros 4000 caracteres. Entonces deberás ejecutar head -c 4K el_quijote.txt. Y si en lugar de ser miles se trata de millones, entonces head -c 4G el_quijote.txt

tail

Esta es la herramienta complementaria a head, porque te permite extraer lo último del archivo, es decir, empezando por el final del archivo. El uso, es similar al de la utilidad anterior,

tail [opciones] archivo

Aquí también hay algunas opciones que son realmente interesantes,

  • -c. Extrae los últimos bytes. También es posible utilizar -c +numero. En este caso lo que hará es extraer desde el byte numero.
  • -n. Igual que el caso anterior pero en lugar de bytes lo realiza con líneas. Igualmente también puedes utilizar -n +numero para extraer desde la línea numero.
  • -f. Con esta opción se va añadiendo texto conforme el archivo va creciendo. Esto es de gran utilidad para seguir un log.

Así, si quieres seguir la evolución de un log, empezando por las últimas 100 líneas,

tail -n 100 -f registro.log

Por supuesto tanto head como tail, muestran por pantalla el resultado de la extracción. Si lo que quieres es guardarlo en un archivo, lo que deberás hacer es redirigir la salida. De esta manera si queremos guardar las 10 últimas líneas del Quijote en un nuevo archivo, lo que debemos ejecutar es,

tail -n 10 > ultimas_lineas.txt

sort

Como te puedes imaginar, esta herramienta para procesar texto, te permite ordenar las líneas de un archivo. Al igual que las anteriores, el resultado de esta ordenación se muestra por pantalla. Si quieres guardar el resultado de este ordenamiento, deberás redirigir la salida.

Algunos usos interesantes de sort,

  • sort archivo.txt. Ordena las líneas del archivo en orden ascendente.
  • sort -r archivo.txt. Igual que en el caso anterior pero en orden descendente.
  • sort --ignore-case -r archivo.txt. También lo ordena de forma descendente pero sin diferenciar entre mayúsculas y minúsculas.
  • sort -n archivo.txt. En este caso el ordenamiento lo hace de forma numérica.
  • sort -h archivo.txt. Igual que el caso anterior, pero el orden es humano. ¿Que quiere decir un orden humano?. Después del 1 viene el 2. Mientras que en otro ordenamiento, después del 1 vendría el 10.

Ahora te puedes entretener jugando con El Quijote, ordenando su contenido en orden ascendente y descendente. Con el siguiente ejemplo, lo ordenarías de forma descendente y sin tener en cuenta mayúsculas y minúsculas.

sort -r --ignore-case el_quijote.txt

uniq

Muestra las líneas únicas de un archivo. Esto lo hará siempre y cuando las líneas sean adyacentes. Vamos que lo que hace esta herramienta es quitar las líneas repetidas que estén seguidas. De esta forma de utilizar esta herramienta es preciso qtldrue ordenes el archivo.

Así por ejemplo, si tienes un archivo con el siguiente,

1
2
3
1
2
3

Y ejecutas uniq archivo.txt obtendrás como resultado el mismo archivo. Para conseguir el resultado que es esperas tendrás que encadenar la ejecución de dos herramientas, tal y como te comenté en el capítulo 6 sobre redirigir entradas y salidas. En una línea de comando este se resume en,

sort archivo.txt | uniq

Al igual que otras herramientas uniq también tiene algunas opciones que modifican su comportamiento. Así algunas de estas opciones son las siguientes,

  • -u muestra únicamente las líneas únicas. Si todas las líneas están repetidas no mostrará ninguna.
  • -d en este caso muestra solo las líneas duplicadas. Este es justo el caso completamente opuesto al anterior. En este sentido, si no hay ninguna duplicada no mostrará nada.
  • -c cuenta el número de repeticiones de cada línea y lo muestra junto a la línea. Primero indica el número de repeticiones y a continuación la línea.

Si por ejemplo quisieras mostrar el número de repeticiones de cada línea, junto a la línea y además ordenarlo de mayor a menor, tendrías que realizar el siguiente encadenamiento,

sort archivo.txt | uniq -c | sort -nr

fmt

Con esta herramienta lo que conseguirás es reformatear un archivo, básicamente uniendo párrafos. Es decir, al fin y al cabo, lo que hace es eliminar saltos de línea. Pero además te permite limitar el máximo número de caracteres por línea forzando un salto de línea.

Algunas de las opciones de esta herramienta son las siguientes,

  • -w limita el número de caracteres al indicado.
  • -s solo une aquellas líneas que tienen un número de caracteres inferior al indicado.
  • -u ajusta el número de espacios entre palabras a 1

Un par de ejemplos sencillos. Partiremos de un archivo ejemplo.txt con el siguiente contenido.

1
2
3
4

Si ejecutamos fmt ejemplo.txt, obtendremos

1 2 3 4

Ahora podríamos extraer el penúltimo elemento de la lista

fmt ejemplo.txt | awk '{print $(NF-1)}'

Aunque esto también lo podríamos hacer con la combinación de tail y head de la siguiente forma,

tail -n 2 ejemplo.txt | head -n 1

tr

Esta herramienta para procesar texto, se encarga de reemplazar o borrar un carácter o conjunto de caracteres por otro u otros. Para borrar tienes que utilizar la opción -d.

Para los siguientes ejemplos vas a recurrir de nuevo a El Quijote, y como primer paso vas a sustituir todas las apariciones de Q por X,

tr Q X < el_quijote.txt

Ahora tienes El Xuijote. Si lo que quieres realmente es El Xijote, probablemente deberías haber utilizado sed en lugar de tr,

sed 's/Quijote/Xijote/g' el_quijote.txt

Otro ejemplo. Reemplaz toddas las vocales por la o. Para ello, ejecuta la siguiente orden,

tr aeiu oooo el_quijote.txt

Con el siguiente resultado,

obro ól ondovo (con pordón so moonto)
osto monso oscodoro, tros ol monso
cobollo Rocononto y tros so dooño.

Fíjate bien en el comportamiento de esta herramienta al sustituir los caracteres acentuados. Yo desde luego no esperaba este resultado.

Por último, si queremos borrar todas las vocales de El Quijote,

tr -d aeiou < el_quijote.txt

cat

Esta herramienta te permite mostrar por pantalla el contenido de un archivo. Otra posibilidad de esta herramienta es concatenar archivos. Por supuesto, no solo te permite mostrarlo en pantalla, sino que también te permite guardar en un archivo, para lo que tendrás que redirigir la salida estándar, como he comentado anteriormente.

  • cat archivo.txt muestra el contenido del archivo por pantalla
  • cat archivo.txt > archivo2.txt guarda el contenido de un archivo en otro.
  • cat archivo.txt >> archivo2.txt añade el contenido de un archivo a otro archivo.
  • cat archivo1.txt archivo2.txt > archivo3.txt concatena dos archivo y los guarda en un tercer archivo.
  • cat archivo1.txt archivo2.txt >> archivo3.txt lo mismo que en el caso anterior pero esta vez lo añade al contenido existente del tercer archivo.

split

Si cat te permite unir archivos, split es la herramienta opuesta, puesto que su funcionalidad es precisamente la de dividir archivos. Esta división te la permite realizar por número de archivos resultantes, número de líneas o tamaño. Por otro lado, si no defines un prefijo, los archivos resultantes los nombrará como xaa, xab, xac,....Así, las opciones disponibles son las siguientes,

  • -l te permite indicar el número máximo de líneas por archivo resultates.
  • -n con esta opción puedes indicar el número de archivos resultantes.
  • -b esta opción te permite definir el tamaño máximo en bytes resultante de los archivos. Puedes indicar K, M, G para indicar ese tamaño.

Así por ejemplo si queremos dividir El Quijote en archivos de 100K, ejecutaremos,

split -b 100K el_quijote.txt quijote_

Lo que te dará como resultado

quijote_aa
quijote_ab
quijote_ac
...

wc

Esta herramienta para procesar texto, la puedes utilizar para contar palabras, bytes o líneas en uno o varios archivos. Así, las opciones que permite esta herramienta son las siguientes,

  • -c cuentas los bytes
  • -m esta opción cuenta los caracteres
  • -l cuenta las líneas
  • -w si lo que quieres es contar palabras esta es tu opción.

Por ejemplo, si lo que quieres es conocer cuantas palabras contiene cada uno de los archivos de un directorio, tan solo tienes que ejecutar,

wc -w *

expand y unexpand

Un par de herramientas realmente útiles para los que nos dedicamos a escribir código. Lo que permite es convertir tabulaciones en espacios y al revés. El resultado lo muestra por la salida estándar, es decir, por pantalla. Si quisieras guardar el resultado en un archivo, tan solo tienes que redirigir la salida.

Así, expand se encarga de convertir tabulaciones en espacios. Mientras que unexpand se encarga del proceso contrario, es decir, de convertir de espacios en tabulaciones.

En ambos casos es posible definir el tamaño de una tabulación, utilizando la opción t.

paste

Une dos o mas archivos en un nuevo archivo que muestra por las salida estándar. Cada línea del nuevo archivo está construida a partir de las líneas de los archivos originales separados por un tabulador u otro delimitador en el caso de que tu lo definas. Es decir, la primera fila del nuevo archivo, estará formada pro la primera fila de cada uno de los archivos separadas por comas.

Por ejemplo, partimos de dos archivos,

archivo1.txt

abc
def
ghi

archivo2.txt

123
456
789

Si ahora ejecutas

paste archivo1.txt archivo2.txt > archivo3.txt

Y lo muestras por pantalla utilizando cat archivo3.txt, el resultado será el siguiente,

abc    123
def    456
ghi    789

join

join funciona de foma similar a paste pero para unir filas lo hace por la primera columna. Además, necesita que los archivos estén ordenados. Lo mejor es que lo veas con un algunos ejemplos. Para ello voy a utilizar dos archivos,

archivo1.txt

1 abc
2 def
3 ghi

archivo2.txt

1 123
2 456
3 789

Si ahora hacemos join archivo1.txt archivo2.txt el resultado será,

1 abc 123
2 def 456
3 ghi 789

Si no estuviera ordenado alguno de los dos archivos te daría un error. Para probarlo, simplemente cambia en el segundo archivo la línea 2 456 por 3 456 y la 3 789 por 2 789 ¿como? Utilizando lo que has visto hasta ahora… sed

sed 's/^2/3/g' archivo2.txt | sed 's/^3\s7/2 7/g' > archivo3.txt

Si ahora haces join archivo1.txt archivo3.txt te devolverá un error,

1 abc 123
join: archivo3.txt:3: no está ordenado: 2 789
3 ghi 456

Con lo que la primera medida que tienes que adoptar para utilizar esta herramienta es ejecutar sort con cada uno de los archivos que quieras unir.


Más información,

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *