26 diciembre 2005

Nuestras amigas, las Expresiones Regulares (I)

Expresiones regulares o también llamadas a menudo RegExp. Odiadas por muchos, amadas por unos pocos que saben utilizar su poder. Y es que dentro de esa mascara de dificultad o ilegibilidad se esconde un gran potencial.

El origen de las RegExp está en la teoría de autómatas y lenguajes formales, una parte no demasiado sencilla del álgebra que acompaña a cualquier carrera de informática que se precie. Por ello, y por que su notación en ordenador no es demasiado legible, no tienen muy buena fama entre quienes no las conocen.

Según la definición de la Wikipedia, una expresión regular es una cadena que describe un conjunto de cadenas, de acuerdo con unas reglas sintacticas. Comenzaron a usarse en el mundo de la informática dentro de las primeras y potentes aplicaciones del sistema UNIX (por ejemplo el comando grep).

Prácticamente cualquier lenguaje de programación actual cuenta con RegExp en su sintaxis o en sus librerías básicas (menos algunos que se resisten, como el infame Objective-C).

Hoy en día la sintaxis UNIX está anticuada, la más popular y utilizada es la PCRE (Perl Compatible Regular Expression); que como su nombre indican, estan implementadas dentro del lenguaje Perl. Estas son en las que nos centraremos.

Los usos de las RegExp son muy variados, ya que nos permiten tanto validar la estructura de una cadena (pej, un e-mail o fecha, o cosas mucho más complejas) o extraer información (pej, del log de un programa). Incluso podemos utilizarla para describir algun lenguaje de script sencillo, sino queremos crear un compilador completo (y ni así nos libraremos de definirlo con RegExps).

Comencemos con la práctica. Como se menciona en su definición, una RegExp no es más que una cadena con una sintaxis especial. Así, unos cuantos símbolos clave:
  • ^ para indicar un comienzo de linea
  • $ para indicar el finald e una cadena.
  • . para cualquier carácter único.
  • * indicamos una repetición de un elemento 0 o más veces.
  • + indicamos una repetición de un elemento 1 o más veces.
  • \t indica un tabulador
  • \w indica cualquier carácter que pueda formar parte de una palabra
  • \s indica un espacio, tabulador o salto de linea
  • \d indica un dígito
(los tres últimos en mayúscula (\W, \S, \D) indican justo lo contrario)

Así, por ejemplo, una expresión regular que indique una línea con tres caracteres sería "^...$". Si queremos una RegExp que encaje con una cadena que tenga 3 palabras en una línea podemos usar "^\w+ \w+ \w+$". Existe toda una sintaxis compleja que nos permite reconocer cualquier tipo de patrón (bueno, cualquier tipo de patrón que pueda resolver un autómata finito). Para ello, mejor consultar una manual de PCRE.

Estás RegExp nos permiten saber si otra cadena encaja con unas condiciones. Pero las expresiones regulares no solo permiten comprobar, también podemos obtener información de ella. Como en la RegExp "Busco esta informacion :(.*)". Utilizando los parentesis, podemos extraer la información de cada encaje que produzca la RegExp y se encuentre dentro de los parentesis.

Bueno, esto ya se esta haciendo muy largo. En el siguiente post sobre las RegExp, explicaré como usarlas dentro de Perl y de Java, con algún otro ejemplo más concreto. Mientras tanto, podeis echarle un vistazo a los links.

Links de interes
Wikipedia
PCRE Workbench, para prácticar con RegExp
Perl Regulars Expression

1 comentario:

singermornings dijo...

He detectado cierta acritud hacia Objective... :-P

Espero ansioso el post sobre Peeeeerl.