Patrón de expresiones regulares Siette

Este patrón es una versión simplificada en algunos casos y extendida en otros de las expresiones regulares que pueden encontrarse en muchos lenguajes de programación como Java, Javascript, Perl, etc. Una expresión regular no es mas que una forma de definir un lenguaje regular, es decir, un conjunto de secuencias de caracteres.

Expresiones básicas

Los patrones son a su vez cadenas de caracteres, y utilizan como base el mismo alfabeto por lo que es necesario tomar ciertas precauciones al escribir algunos caracteres que tienen un significado especial. En la siguiente tabla se muestran los patrones y el carácter que representan. Siguiendo la notación clásica en esta materia llamaremos “lexemas” a las secuencias de caracteres reconocidas por el patrón.

Caracteres individuales

En general cualquier carácter no especial se representa a si mismo. Los caracteres especiales deben llevar una barra invertida \ en el patrón como indica la siguiente tabla:

Patrón Lexema
\? ?
\+ +
\* *
\| |
\( (
\) )
\{ {
\} }
\[ [
\] ]
\< <
\> >
\# #
\$ $
\\ \

Concatenación

La concatenación de dos expresiones regulares da como resultado otra expresión regular que representa todas las posibles combinaciones de los lexemas de la primera expresión con todos los posibles lexemas de la segunda. A continuación se dan algunos ejemplo simples.

Patrón Lexema
abc abc
a\*c a*c
\\\\
\\

Más adelante se verán nuevos ejemplos.

Disyunción

El carácter especial | representa la alternativa o disyunción, se usa para combinar posibles respuestas en el patrón, por ejemplo:

Patrón Ejemplo de Lexema
a|e|i|o|u i
u
altura|altitud altitud
altura
\+|-|\*|/ +
*

Paréntesis

Los paréntesis tienen la misión de agrupar una misma expresión regular, cambiando las prioridades de operación. Todo lo que esta entre paréntesis se considera como una sola expresión frente a las operaciones de concatenación disyunción.

Patrón Ejemplo de Lexema
alt(o|a) alto
alta
(C|c)ol(o|ó)n Colón
colon
(pa|ma|ra)|(ta|la) pala
mata

Paréntesis cuadrados

Los paréntesis cuadrados, sirven para denotar disyunciones de un solo símbolo, es decir, son simplemente modos abreviados de escribir expresiones que podrían escribirse con paréntesis. Es decir, un paréntesis cuadrado que contenga cinco caracteres indica que cualquiera de estos caracteres puede usarse.

Patrón Ejemplo de Lexema
alt[oa] alto
alta
[aeiou] a
u
[Cc]ol[oó]n Colón
colon

Un caso especial en os paréntesis cuadrados son las secuencias, que se usan cuando el número de caracteres es grande. Por ejemplo la secuancia [A-Z] indica cualquier letra mayúscula (una sola letra

Patrón Ejemplo de Lexema Ejemplo de lexema no reconocido
[a-Z][a-z] El eL
La aL
[1-9][0-9][0-9] 101 007
345 1000
H[0-9]|H1[0-9]|H2[0-3] H0 H00
H17 H107
H23 H24

Llaves

Las llaves {} tienen también un significado especial. Las expresiones que se sitúan entre llaves se entiende que son opcionales, es decir, que pueden aparecer o no en la respuesta. A continuación se muestran como algunos patrones, ejemplos de lexemas válidos y no válidos.

Patrón Ejemplo de lexemas lexemas no válidos
30{km|kilometros} 30 30m
30km km
x={a}{b}{c} x=a x=aaa
x=ac x=ca
x= x=abcabc
{[Cc]rist[oó]bal} [Cc]ol[oó]n Colón Cristotal
cristobal colon colon Cristobal

Comodín

El carácter especial ? se usa para denotar representa a un (uno y sólo uno) símbolo cualquiera, sin especificar cual. ejemplos:

Patrón Ejemplo de lexemas lexemas no válidos
alt? alto alt
alta al
alt+ +alt
x=? x=a x=aaa
x=b x=ca
x=9 x=abcabc
{[Cc]rist[oó]bal} [Cc]ol[oó]n Colón Cristotal
cristobal colon colon Cristobal

Comodín de secuencia

El carácter especial * se usa para denotar una secuencia de cero, uno o más caracteres cualesquiera. ejemplos:

Patrón Ejemplo de lexemas lexemas no válidos
A*Z ABCXYZ ZYXCBA
A+B+Z A
AZ Z
x=30* x=30km 30
x=30m y=30
x=3000 x=00
*[Cc]ol[oó]n Colón Cristotal
cristobal colon colon Cristobal
fernando colon

Permutaciones

El operador + se usa para poder generar permutaciones en el orden de respuesta. Es un operador binario que afecta a las dos expresiones situadas a derecha e izquierda. Dado que el número de permutaciones crece factorialmente con el número de expresiones, a efectos prácticos se limita a 6 el número de expresiones que pueden interoperarse con el operador +, Tenga en cuenta que 6! = 720, pero que 7! = 5040 lo que supone un tiempo de cálculo excesivo para una pregunta.

Patrón Ejemplo de lexemas lexemas no válidos
a+b+c abc ab
bac ac
cba bbb
p[aeiou]+t[aeiou]+l[aeiou] paleta ptl
pelota papa
tapate lapiz

Final de expresión

El carácter especial $ indica el final de la expresión correspondiente al patrón. Sólo se usa internamente, por lo que debe utilizarse la secuencia \$ para incluir este carácter en las respuestas.

Evidentemente, la potencia que ofrece el uso de estas expresiones en la definición de patrones de respuesta está limitado por el grado de tolerancia a fallos que se haya decidido aceptar. Se deja a criterio del profesor el buen uso de estas expresiones. Como consejo general a la hora de crear preguntas de respuesta libre, lo mejor es concretar al máximo posible la pregunta, de manera que no existan muchas ambigüedades.

Ejemplo 1

Enunciado Indique el nombre de alguna novela de Hemingway
Patrón. *(viejo*mar|doblan*campanas|fiesta)*
Respuestas reconocidas El viejo y el mar
Por quién doblan las campanas
París era una fiesta
Fiesta
En la fiesta de Blas
Respuestas no reconocidas Adiós a las armas
Las nieves del Kilimanjaro
Nuestro hombre en la Habana

En ete punto es conveniente revisar las indicaciones sobre el uso de los patrones. Nótese que hay dos tipos de posibles errores en el uso de patrones, señalados en rojo y en azul en el ejemplo anterior: (1) Respuestas incorrectas que se consideran correctas; y (2) Respuestas correctas que se consideran incorrectas.

Ejemplo 2

Enunciado ¿Quién escribio “El Quijote”?
Patrón. {{Don} Miguel {de}} Cervantes {Saavedra}
Respuestas reconocidas Cervantes
Miguel de Cervantes
Don Miguel de Cervantes Saavedra
Miguel Cervantes
Respuestas no reconocidas D. Cervantes
Don Miguel

En muchos casos conviene concretar el enunciado de manera que no quede lugar a ambigüedades y que la respuesta deba ser necesariamente corta y exacta. En el ejemplo anterior, el enunciado podría indicar Escriba el apellido del autor de “El Quijote”.

Ejemplo 3

Enunciado Cuáles son los colores de la bandera de Francia?
Patrón. rojo+blanco+{y}+azul
Respuestas reconocidas rojo blanco y azul
azul rojo y blanco
blanco azul rojo
blanco y azul rojo
y azul rojo blanco
Respuestas no reconocidas blanco y azul y rojo
blanco y azul

Los patrones de respuesta pueden aceptar como correctas algunas expresiones que no son gramaticalmente correctas. Sin duda, si las expresiones se usaran para generar todas las posibles respuestas y proponerlas como ejemplo, este comportamiento sería problemático. Sin embargo, las expresiones están pensadas para su uso contrario, por lo que no es muy importante que puedan reconocer expresiones como “blanco y azul rojo” que no sería gramaticalmente correcta, aunque probablemente no la emplearía ningún alumno. Tampoco parece probable obtener una respuesta como “blanco y azul y rojo”. No obstante, si ocurriera deben seguirse las recomendaciones del uso de los patrones y refinar el patrón.

Ejemplo 4

Enunciado Indique los años durante los que trascurrió la segunda guerra mundial
Patrón. *1939*1945*
Respuestas reconocidas Entre 1939 y 1945
Desde 1939 hasta 1945
Empezo en 1939 y termino en 1945
1939-1945
1939-40-41-42-43-44-1945
193987654321945
Respuestas no reconocidas 1939-45
Empezó en 1939 y duró 6 años

Ejemplo 5

Enunciado María compró tres docenas de huevos y le dió la mitad a Carmen. ¿Cuantos huevos le quedan a María?
Patrón. {{una} docena y (media|seis|6)|dieciocho|18}{{de} huevos}
Respuestas reconocidas Una docena y media
18 huevos
docena y 6 de huevos
una docena y seis
Respuestas no reconocidas doce y seis
dos docenas menos media

Se da el mismo caso que en el ejemplo anterior con expresiones como “18 de huevos” que no sería gramaticalmente correctas, pero que probablemente no la emplearía ningún alumno.

Patrones con números

Los números se tratan de igual forma que los demás caracteres en los patrones de respuesta, por tanto, cuando en un patrón de respuesta aparece una secuencia de dígitos, no se analiza su contenido semántico, sino solamente la expresión considerada como una secuencia de caracteres.

Ejemplo 6

Enunciado ¿Cuál es el resultado decimal de dividir 10 entre 3?
Patrón. 3.3|3.33|3.333*
Respuestas reconocidas 3.3
3.333
3.33333333
0.333999999999
Respuestas no reconocidas 10/3
333E-2

Nótese que aunque es una manera muy extraña de expresarlo técnicamente sería correcta la respuesta “333E-2” que técnicamente es lo mismo que 333 * 10-2. Otros patrones alternativos como 3.3{3}{3} tienen problemas similares.

Ejemplo 7

Enunciado ¿Cuál es el valor de la constante $\pi$?
Patrón. 3.14|3.1416|3.14159{2{[67]}}
Respuestas reconocidas 3.14
3.1416
3.1415927
Respuestas no reconocidas 3.1415926536
+3.1416

Como puede verse, la precisión de la respuesta plantea un problema a la correspondencia meramente lexica.

Para resolver este problema que plantea la habitual interpretación de las secuencias de caracetres que representan digitos como valores numéricos, se han definido en este patrón expresiones númericas. Estas expresiones son especialmente adecuadas cuando se trabaja con números reales, ya que permiten definir la precisión con la que se aceptaran las entradas del usuario. Las expresiones numéricas pueden concatenarse normalmente dentro de los patrones de respuesta. Un número puede definirse en el patrón de dos formas:

– Definiendo explícitamente el rango de aceptación:

<número|número> o bien usando la sintaxis antigua #número#número#

en donde, número representa cualquier secuencia de caracteres que constituya una constante numérica entera o real en Java. El primer número debe ser mayor que el primero. Por ejemplo, el patrón : <1939|1945>, acepta cualquier número comprendido entre 1939 y 1945, ambos inclusive. ( en la versión anterior de Siette, compatible con la actual, el patrón se escribiría #1939#1945# )

– Definiendo el porcentaje de error admisible:

<número%número> o bien usando la sintaxis antigua: #número#número%

en donde el primer numero representa la base de cálculo y el segundo el error porcentual admitido. Por ejemplo, para aceptar cualquier aproximación al número π con un error menor del 1 por ciento, se puede usar el patrón: &lt;3.14%1&gt; ( en la versión anterior de Siette, compatible con la actual, el patrón se escribiría #3.14#1% )

Los patrones de respuesta numéricos siempre se comprueban mediante un intervalo, aunque éste puede ser tan pequeño como se desee, incluso 0. Internamente cuando se encuentra una secuencia de dígitos en la entrada y se han definido patrones numéricos, la secuencia de dígitos se extrae de la entrada y se calcula si encaja o no con la expresión numérica

Patrones con magnitudes (Números con unidades)

Para ciertas aplicaciones, la respuesta numérica puede no ser suficiente. Por ejemplo, si se pregunta la velocidad de un vehículo, la respuesta podría expresarse en m/s o en km/h o en cualquier otra magnitud. Además, cuando la respuesta incluye cantidades grandes o pequeñas, la respuesta podría expresarse de distinta manera, por ejemplo la velocidad de la luz, es aproximadamente 300,000 km/s, que es la expresión más habitual, pero también podría expresarse como 3*108 m/s.

Unidades

Para expresar las unidades de una determinada magnitud Siette utiliza las expresiones:

<número unidades|número>

<número unidades%número>

En donde las unidades, es una cadena de caracteres que representa una unidad de medida. La lista de unidades de medida incluye unas 500 de las más comunes unidades de longitud, velocidad, masa, volumen, tiempo, etc.

Para determinar si la respuesta a una pregunta es correcta, pueden ocurrir varios casos:

En los siguiente ejemplos 81 y 8b se muestra la diferencia entre indicar las unidades dentro y fuera del patrón:

Ejemplo 8a

Enunciado Un coche tarda hora y media en recorrer la distancia entre dos ciudades que distan 108 km. ¿A que velocidad media circula? (expresar la velocidad en m/s)
Patrón. <20%0> {m/s}
Respuestas reconocidas 20
20 m/s
Respuestas no reconocidas 72 m/s
72 km/h
20 km/h

Ejemplo 8b

Enunciado Un coche tarda hora y media en recorrer la distancia entre dos ciudades que distan 108 km. ¿A que velocidad media circula?
Patrón. <20 m/s%0>
Respuestas reconocidas 20
20 m/s
72 km/h
Respuestas no reconocidas 72 m/s
20 km/h

Constantes numéricas

Cuando se escribe un número usando solamente los caracteres que aparecen en un teclado ocurren distintas formas de expresar un mismo número. En el patrón numérico de Siette se intenta reconocer de manera “inteligente” el número que se ha intentado expresar con la respuesta, usando posibles variantes.

El uso de números con decimales y exponente puede combinarse con las unidades indistintamente.

Ejemplo 9

Enunciado ¿Cuál es la velocidad de la luz?
Patrón. <3E5 km/s%10>
Respuestas reconocidas 300000 km/s
3E5 km/s
186E3 nudos
Respuestas no reconocidas 3E8
3E5 km/h