|
|
|
Una expresión regular, a menudo llamada también patrón,
es una
expresión
que describe un conjunto de cadenas sin enumerar sus elementos. Por
ejemplo, el grupo formado por las cadenas Handel, Händel y Haendel se
describe mediante el patrón "H(a|ä|ae)ndel". La mayoría
de las
formalizaciones proporcionan los siguientes constructores:
alternación
Una barrar vertical separa las alternativa. Por ejemplo,
"marrón|castaño" casa con marrón o castaño.
cuantificación
Un cuantificador tras un carácter especifica la frecuencia con la que
éste
puede ocurrir. Los cuantificadores más comunes son +, ? y *:
+ El signo más indica que el carácter al que sigue debe aparecer
al
menos una vez. Por ejemplo, "ho+la" describe el conjunto infinito
hola,
hoola, hooola, hoooola, etcétera.
? El signo de interrogación indica que
el carácter al que sigue puede aparecer como mucho una vez. Por
ejemplo,
"ob?scuro" casa con oscuro y obscuro.
* El asterisco indica que el
carácter al que sigue puede aparecer cero, una, o más veces.
Por
ejemplo, "0*42" casa con 42, 042, 0042, 00042, etcétera.
agrupación (register groups)
Los paréntesis pueden usarse para definir el ámbito y
precedencia de los demás operadores. Por ejemplo, "(p|m)adre"
es lo
mismo que "padre|madre", y "(des)?amor" casa con amor
y con desamor.
Lo que se agrupa entre paréntesis se llama "register group"
(ver
Regex Coach, en el tab control - seleccion y luego 1,2 etc, y en la
ayuda)
y es posible encontrar la coincidencia exclusiva de uno de
los register group ademas de la expresión completa:
Ej:
^(.*)(\d+\.\d{2})(.*)$
tiene tres grupos (juegos de paréntesis)
Hay un potencial problema con esto de los grupos, con algo llamado "las
expresiones regulares son greedy), de modo que el grupo 2 de la
expresión regular anterior no coincide bien en este ejemplo:
Charge $229.95, and get a receipt.
(Aunque la expresión regular completa si funciona)
La solución es usar reluctant matches, con los operadores ??, *? y
+?
que emparejan el mínimo texto posible. La solución al ejemplo
anterior
es hacer reluctant el primer grupo, así:
^(.*?)(\d+\.\d{2})(.*)$
Los constructores pueden combinarse libremente dentro de la misma
expresión, por lo que "H(ae?|ä)ndel" equivale a "H(a|ae|ä)ndel".
La sintaxis precisa de las expresiones regulares cambia según las
herramientas y aplicaciones consideradas, y se describe con más detalle
a continuación. (tomado de wikipedia)
CHARACTER CLASS []
Aqui los metacaracteres pierden su significado especial.
[abc] match a,b o c. O c,b,a etc sin importar el orden
[a-c] " " "
[a-z] cualquier caracter en minúscula
[a$] match la a y el $ como metacaracter. En [] todo se toma literal.
[^$] match cualquier caracter menos el $
METACARACTERES
. cualquier caracter, menos el nueva línea
^ niega o el principio de línea (después de un newline character)
* cero o mas veces el caracter, class character o grupo anterior
+ una " " " " " "
? una o cero veces " " " "
{ repeticiones dando rangos
[] character class
\ para escapar estos metacaracteres
| separa alternativas: bien|mal (con las palabras completas
() como en matemáticas
$ el final de linea
\A Al principio de la cadena
\Z Al final de la cadena
\b Solo palabras completas (no inmersas en otra)
\B Lo contrario, solo cuando no es una palabra completa
SECUENCIAS
\d equivale [0-9]
\D " [^0-9]
\s " [\t\n\r\f\v] cualquier espacio en blanco
\S " [^\t\n\r\f\v] que NO sea cualquier espacio en blanco
\w " [a-zA-Z0-9_] cualquier caracter alfanumérico
\W " [^a-zA-Z0-9_] cualquier caracter NO alfanumérico
Estas secuencias se pueden usar en characte class, ej:
[\s,.] match cualquier espacio en blanco o "," o "."
REPETICIONES con * + ? {}
ca*t match ct cat caaat
a[xy]*z match a, cero o mas repeticiones de x o y y la z
{3,10} al menos 3 y como máximo 10
LOOKAHEAD ASSERTION
(?=...) Positive lookahead assertion. This succeeds if the contained
regular expression, represented here by ..., successfully matches at
the
current location, and fails otherwise. But, once the contained
expression has been tried, the matching engine doesn't advance at all;
the rest of the pattern is tried right where the assertion started.
(?!...) Negative lookahead assertion. This is the opposite of the
positive assertion; it succeeds if the contained expression doesn't
match at the current position in the string.
EN PYTHON:
El mejor documento es el howto: http:/www.amk.ca/python/howto/regex
Ya lo tengo local: Regular Expression HOWTO-Python.htm
Para evitar la plaga de los \\\\ : r"\\section" <=> "\\\\section"
------------------------------------------------------------------------
EJEMPLOS:
1. Para coincidir con filename.ext:
.*[.].*$
Cero o mas caracteres de lo que sea, un punto, mas de lo primero y un fin
de linea.
2. Encontrar algo que tenga unlink y tambien marca, como en
if(unlink("marca") == -1), pero con caracteres entre las dos.
unlink.+marca, egrep: unlink.+marca *.cpp
unlink mas uno o mas caracteres de lo que sea mas marca
2.5 Que saque las lineas que tengan las frases:
"201.232.72" y "18/Nov" y "claroline",
Para extractar del log de acceso del apache, access_log, los
accesos que han hecho desde la direccion 201.232.72 el dia 18 de nov y a las
paginas de claroline,
egrep '201[.]232[.]72.*18/Nov.*claroline' o
egrep '201\.232\.72.*18/Nov.*claroline'
\. es escapar el .
.* es 0 o mas caracteres cualquiera
3. Encontrar o unlink o marca:
unlink|marca
Saque las lineas que tengan las palabras unlink o marca:
egrep: "unlink|marca" *.cpp
4. Para coincidir los archivos que no tengan extensión 'bat':
.*[.](?!bat$).*$
The LOOKAHEAD ASSERTION means: if the expression bat doesn't match at
this point, try the rest of the pattern; if bat$ does match, the whole pattern
will
fail. The trailing $ is required to ensure that something like
"sample.batch", where the extension only starts with "bat",
will be
allowed.
5. Para coincidir los archivos que no tengan extensión 'bat'ni "exe":
.*[.](?!bat$|exe$).*$ una LOOKAHEAD ASSERTION con |
6. Usado en la ayuda en WEB de python
http://www.python.org/peps/pep-0263.html
a partir de la versión 2.3 para indicar el encode del archivo fuente,
ver comprima .py
coding[:=]\s*([-\w.]+)
la palabra coding, seguida de
\s 0 o mas espacios en blanco
seguido de
([-\w.]+)
Una o mas ocurrencias de cualquiera de estos:
- el guion
\w cualquier caracter alfanumérico
. el punto
ejemplo coding: utf-8
Un ejemplo práctico (Tomado de desarrolloweb.com para php)
Hemos dicho que las expresiones regulares son uno de los instrumentos
mas útiles en cualquier lenguaje de programación. ¿Para
que podemos
usarlas?. Uno de sus usos mas típicos es el de validar entradas de
datos
que los visitantes de una página puedan mandarnos a través de
formularios html. El ejemplo mas corriente es el de una dirección
email.
Imaginemos que queremos filtrar las direcciones introducidas por los
visitantes, para evitar introducir en la base de datos la típica
dirección basura ghghghghghghg. Todos sabemos la estructura de una
dirección email, formada por la cadena nombreusuario, el signo @ y
la
cadena nombredominio. Tambien sabemos que nombredominio esta formado
por
dos subcadenas, 'nombredomino', un '.' y un sufijo 'com', 'net', 'es' o
similar. Por tanto la solución a nuestro problema es idear una
expresión
regular que identifique una dirección email valida típica, y
confrontarla con la cadena (dirección email) pasada por el visitante
Por
ejemplo:
<?
^[^@ ]+@[^@ ]+.[^@ .]+$
?>
Vamos a diseccionar nuestra expresión regular:
<?
^ // queremos decir que el primer carácter que buscamos
// debe estar al principio de la cadena a comparar.
[^@ ] // ese primer signo no debe ser ni el signo @
// ni un espacio
+ // y se repite una o mas veces
@ // luego buscamos el signo @
[^@ ]+ // Seguido de otro signo que no es un @ ni un
// espacio y se repite una o mas veces
. // Seguido de un .
[^@ .] // Seguido de un carácter que no sea ni @,
// ni espacio ni punto
+$ // Que se repite una o mas veces y el último esta
// al final de la cadena
?>
Y para comprobarlo en la práctica, usamos una de las funciones de
php
relacionadas con las expresiones regulares:ereg(). Acudiendo al manual
php, podemos averiguar que esta función tiene la siguiente sintaxis:
ereg (string pattern, string string) Busca en string las coincidencias
con la expresión regular pattern. La búsqueda diferencia entre
mayúsculas y minúsculas. Devuelve un valor verdadero si se encontró
alguna coincidencia, o falso in no se encontraron coincidencias u
ocurrió algún error. Podríamos usar esta funcion para
un validador
email
con algo asi como:
<?
// establecemos una secuencia condicional: si la variable $op no existe
y
// es igual a "ds", se muestra un formulario
if ($op != "ds") { ?>
<form>
<input type=hidden name="op" value="ds">
<strong>Tu email:</strong><br />
<input type=text name="email" value="" size="25"
/>
<input type=submit name="submit" value="Enviar" />
</form>
<?
}
// Si $op existe y es igual a "ds"m, se ejecuta la función
ereg
buscando
// nuestra cadena dentro del patrón $email que es la direccion enviada
por
// el usuario desde el formulario anterior
else if ($op == "ds")
{
if (ereg("^[^@ ]+@[^@ ]+.[^@ .]+$", $email ) )
{
print "<BR>Esta dirección es correcta: $email"; }
else {echo "$email no es una dirección valida";}
}
?>
No hace falta advertir que se trata de un ejemplo muy elemental, que
dará por válida cualquier dirección email que tenga una
mínima
apariencia de normalidad (por ejemplo, daria por valida
'midireccionnn@noteimporta.commm')