Está en la página 1de 9

Curso de Informática III; Notas de Clase; Dr. Cyrano Ruiz Cabarrús, Ph.D.

TEMA 2: LENGUAJES
Al inicio de la computación, hablar de “lenguajes de programación” resultaba
confuso y hasta superfluo. En efecto, la programación de los primeros
computadores se reducía a conectar alambres y era percibida de una manera muy
similar a la forma como se opera un aparato mecánico. Luego, mediante el
concepto de programa almacenado, la programación avanzó un salto cuántico. Sin
embargo, a pesar de que los programas y datos ya residían en la memoria del
computador y permitían un proceso de programación más ágil y flexible, los
lenguajes de programación aún resultaban demasiado simples para requerir de
una sustentación teórica de tipo matemático. En esos albores de la computación,
los primeros lenguajes eran del tipo que hoy se denominan de “nivel bajo”, es decir
virtualmente idénticos a los lenguajes máquina. No fue sino posteriormente, que
se empezó a gestar la idea de desarrollar un lenguaje de “nivel alto”, por medio del
que se escribieran programas de computación que resultaran fáciles de entender,
en un estilo parecido a los idiomas humanos y, sobre todo, independientes del
lenguaje máquina.

Este proyecto de desarrollar lenguajes de alto nivel en programación fue lo que


motivó de gran manera a formalizar la Teoría de Lenguajes. Los científicos de la
computación de ese entonces utilizaron teorías que habían sido formuladas en el
campo de la Matemática Discreta y de la Lógica Matemática, para empezar a
fundar las bases de la Teoría de los Lenguajes de Programación. Fue advertido
rápidamente, que proponer un lenguaje de alto nivel no podría resultar en algo
tangible y práctico a menos que se construyera, en paralelo, una “máquina”, es
decir un programa que pudiera leer y analizar información escrita en este nuevo
lenguaje de alto nivel y traducirla al lenguaje que “nativo” del computador,
conocido como “lenguaje máquina”. Este logro resultaría uno de los avances más
importantes en la computación pero antes de conseguirlo era necesario formalizar
y sistematizar el significar de “lenguaje”.

Aunque el término “lenguaje” posee un significado bastante claro en el sentido


intuitivo o informal, tratar de formalizar matemáticamente su definición resulta más
complejo. ¿Qué es un lenguaje? La respuesta, desde el punto de vista formal-
matemático es lo que ocupa la atención en el presente capítulo. Esta definición
constituye la piedra angular sobre la cual se construirán los temas del resto del
libro, como los que surgen en el estudio de la Teoría de Lenguajes y los
respectivos Modelos de Máquinas Abstractas que reconocen y generan estos
lenguajes.

En un sentido amplio, el vocablo de “lenguaje” está presente en todas partes


donde se precise de comunicación. Si bien esto resulta relativamente evidente,
también existen casos en que los lenguajes no son utilizados con fines de
comunicación sino en contextos donde se requiere sólo una codificación de
información. En la primera categoría se incluyen, por ejemplo, a los idiomas que
utilizan los seres humanos para que se comuniquen entre sí o el lenguaje de clave

1
Curso de Informática III; Notas de Clase; Dr. Cyrano Ruiz Cabarrús, Ph.D.

Morse. En la segunda clase pueden incluirse, por citar un par de ejemplos, los
mismos lenguajes de programación o las secuencias genéticas de los genomas.
En esta última categoría de lenguajes, el propósito de su empleo no es
precisamente el de comunicación sino que el de codificar información que permita
generar programas o seres vivientes que interactúen con su entorno y de
determinada manera.

En el contexto de la Teoría de la Computación y en particular de la Teoría de


Lenguajes y Máquinas, se entenderá que todo lenguaje posee dos dimensiones
esenciales inherentes. La primera se refiere a la forma de escribir correctamente
las oraciones del lenguaje en tanto que la segunda al significado que puede ser
atribuido a dichas oraciones. Debido a que el concepto de lenguaje se maneja en
distintas disciplinas del saber, resulta preciso aclarar que, dependiendo del
contexto, las definiciones mostrarán diferencias y los mismos vocablos se
utilizarán de manera distinta.

Para los propósitos de este libro, las dos dimensiones de un lenguaje se definen
de la siguiente forma:

1. Sintaxis: Se refiere a la forma, es decir, a la manera en que se formulan o


escriben correctamente las oraciones utilizando los signos permitidos en el
orden adecuado.

2. Semántica: Se refiere al significado, es decir, lo que debe darse a entender


por medio de estas secuencias de signos.

Se hace hincapié en que la primera dimensión enfoca la forma en que se van


formando correctamente las “oraciones”, siguiendo ciertas reglas, en tanto que a la
segunda dimensión le compete el significado o interpretación de dichas
“oraciones” en la comunicación o transmisión del lenguaje.

Para ilustrar esta diferencia, se puede considerar el caso de un lenguaje de


programación, por ejemplo Pascal. En este caso, el programa llamado compilador
de Pascal, se utiliza para verificar que un programa escrito en este lenguaje se
encuentre libre de errores sintácticos, es decir esté “bien” escrito y sigua las reglas
propias de la sintaxis de lenguaje Pascal. En caso de detectar errores, el
compilador debe indicarlos para que el programador pueda corregirlos o
eliminarlos. Una vez validada la sintaxis, el compilador genera código de lenguaje
máquina, según la semántica o interpretación que se realice de la sintaxis del
programa. Ambas fases, el análisis sintáctico y la traducción al lenguaje máquina,
son importantes y definen en gran medida el trabajo y propósito del compilador de
Pascal.

2
Curso de Informática III; Notas de Clase; Dr. Cyrano Ruiz Cabarrús, Ph.D.

Aquí pueden resaltarse los dos conceptos fundamentales que se desarrollan a lo


largo del presente libro: el de “lenguaje” y el respectivo de las “máquinas1” que
reconocen y analizan estos lenguajes. En el ejemplo anterior, el lenguaje era
precisamente el propio lenguaje Pascal, en tanto que la “máquina”
correspondiente era el compilador de Pascal.

En el sentido anterior, se establece una correspondencia entre lenguajes y


máquinas. Esta relación se refleja también en la complejidad relativa entre un
lenguaje determinado y la “máquina” que es capaz de reconocerlo. Cuando los
lenguajes son sencillos, es decir, cuando pueden definirse por medio de pocas
reglas sintácticas y tienen expresión bastante limitada, las máquinas
correspondientes que los analizan y reconocen, son también igualmente sencillas.
Por el contrario, al aumentar la complejidad sintáctica de un lenguaje al igual que
su poder de expresión, también las máquinas correspondientes se hacen más
complejas.

El resto del capítulo pretende formalizar la definición de la sintaxis de un lenguaje.


Para esto, se principia por definir un alfabeto y luego, de forma constructiva, se va
construyendo la estructura de definiciones que da lugar al concepto formal de
lenguajes en sí. La matemática empleada aquí se apoya fuertemente en la Teoría
de Conjuntos, en el Principio de Inducción Matemático y en las Definiciones
Recursivas, temas desarrollados anteriormente.

ALFABETOS

La sintaxis de un lenguaje usualmente se define en forma gradual e incremental.


En otras palabras, los elementos que intervienen en la formación de las oraciones
tienen que ser presentados en forma progresiva, al definir primero aquellos que
son más simples para luego construir términos más complejos a partir de éstos.
Así, se aumenta el grado de complejidad en las descripciones sintácticas,
basándose en la combinación de elementos sintácticos más sencillos definidos
anteriormente. Por ejemplo, en el idioma español, para definir lo que es una
oración, es necesario clarificar previamente lo que es sujeto, predicado o artículo,
por ejemplo, todos éstos conceptos más simples de definir que el de oración.

En su nivel más elemental, la sintaxis de todo lenguaje empieza a definir sus


elementos “atómicos”, es decir, aquellos cuya presentación no precisan una
descomposición en elementos más sencillos. Estos elementos “atómicos” se
conocen como “letras” y pertenecen a un conjunto que se denomina “alfabeto”, a
partir del cual se forman todas las construcciones sintácticas del lenguaje.

1
En todo el libro, el término “máquina” deberá ser interpretado en un sentido matemático y no
físico. En otras palabras, en el contexto de la Teoría Matemática de la Computación, una
“máquina” no es otra cosa que un modelo abstracto cuyas reglas de construcción y operación
permiten determinar si una oración pertenece o no a un lenguaje.

3
Curso de Informática III; Notas de Clase; Dr. Cyrano Ruiz Cabarrús, Ph.D.

Se define el alfabeto de un lenguaje, usualmente identificado por Σ, como un


conjunto finito y no vacío, cuyos elementos se denominan “letras”, y comúnmente
se representan por las primeras letras de nuestro alfabeto usual, es decir: a,b,c,
etc...

Algunos ejemplos de alfabetos son nuestro “abecedario usual”, el alfabeto binario


cuyas dos únicas letras son los dígitos “0” y “1”, así como los cuatro elementos
básicos del genoma: adenina A, citosina C, guanina G y tiamina T, por citar
solamente algunos.

En cada caso, como se explicó anteriormente, el alfabeto es un conjunto básico a


partir del cual se forman estructuras sintácticas más complejas, según las reglas
correspondientes establecidas para cada lenguaje.

CUERDAS

Como se explicó anteriormente, la sintaxis de un lenguaje se define


progresivamente, basándose en la combinación de elementos más sencillos,
definidos previamente. Las letras de un lenguaje, que fueron presentadas como
los elementos “atómicos”, pueden combinarse, yuxtaponiéndose, para formar
“cadenas” o “cuerdas”. Para propósitos de este libro, el concepto de cuerda puede
ser presentado satisfactoriamente en forma intuitiva y directa2.

Dado un alfabeto Σ, una cuerda se define como una secuencia, es decir una
yuxtaposición, arbitrariamente larga, de letras de ese alfabeto. Por necesidades
teóricas, se postula también la existencia de la secuencia nula o “cuerda nula”
representada por λ (que algunos autores denominan ε) y que para fines prácticos
podrá ser conceptuada como una cuerda de longitud cero, es decir una cuerda sin
letras.

Para propósitos de notación, usualmente se emplean las últimas letras de nuestro


alfabeto “usual” u, v, w, etc... para identificar cuerdas. En particular, las letras de
un alfabeto son también cuerdas del mismo (secuencias de largo uno). También
resulta útil señalar que en el contexto de la Teoría de Lenguajes, el término
“cuerda” puede intercambiarse con los términos “palabra” u “oración”.

Dado un alfabeto Σ, el conjunto de todas las cuerdas, de longitud arbitraria,


formadas a partir de las “letras” de Σ, incluyendo la cuerda nula, se denota como:

2
Alternativamente, se puede definir más formalmente la noción de cuerda. Para esto se definen en
forma recursiva los conjuntos: A0 = ∅, An = An-1 ∪ { n } para todo entero natural n ≥ 1 (es decir, An =
{1, 2, 3, ....., n}). Tomando esto como base, se procede a definir una secuencia como una función
de un conjunto Ai sobre Σ. El formalismo matemático de esta definición resulta excesivo e
innecesario para los propósitos del presente libro.

4
Curso de Informática III; Notas de Clase; Dr. Cyrano Ruiz Cabarrús, Ph.D.

Σ* (“closure”, “cerradura” o “clausura” de Kleene) del alfabeto3. El conjunto Σ+ se


define de la misma manera, excepto que éste no incluye la cuerda nula.

A pesar de que cualquier alfabeto es finito por definición, el conjunto de cuerdas


formado a partir de él es claramente infinito. De hecho, la clausura de Kleene
define el universo de todas las cuerdas posibles de un alfabeto, universo dentro
del cual podrán identificarse subconjuntos interesantes. En el cuento de ficción
titulado: “La Biblioteca de Babel” que figura en el libro: “El Jardín de Senderos que
se Bifurcan”, el escritor Jorge Luis Borges postuló la existencia de una biblioteca
infinita, que contenía libros de todos los tamaños posibles. Cada libro podía
conceptuarse en realidad como una secuencia de letras del abecedario. Claro
está, la inmensa mayoría de estos volúmenes era completamente ininteligible. Sin
embargo, algunos pocos libros eran secuencias bien redactadas, pero carentes de
significado. Otros, más reducidos en número, eran libros bien redactados y con
algún significado. Por fin, una minoría increíblemente diminuta dentro de esa
infinita biblioteca, eran las obras escritas en algún momento de la historia por los
filósofos, escritores y artistas conocidos y desconocidos.

En el fondo, la Biblioteca de Babel imaginada por Borges resulta ser una vívida
ilustración de los alcances de la definición de la clausura de Kleene de un alfabeto
cualquiera.

OPERACIONES CON CUERDAS

Siguiendo la idea de construir las definiciones sintácticas de un lenguaje a partir


de la combinación de elementos más sencillos, es necesario entender las maneras
en que las cuerdas de un lenguaje pueden combinarse para producir cuerdas más
largas o complejas.

Sean dos cuerdas w, v de un alfabeto Σ. Se exponen a continuación las


operaciones usuales entre ellas. Estas definiciones son presentadas en forma
intuitiva y luego, cuando conviene, son formalizadas al utilizar un estilo de
definición recursivo. Por cierto, muchas veces son precisamente estas definiciones
recursivas las que se emplean en las demostraciones con el fin de usar el PIM
(Principio de Inducción Matemática).

1. La concatenación de dos (o más) cuerdas se define como la cuerda


formada yuxtaponiéndolas, en el orden indicado. Es decir, en el caso de
dos cuerdas:

Si: w = a1a2...an y v = b1b2...bm, entonces: wv = a1a2...an b1b2...bm

3
El nombre de Kleene se deriva del matemático Stephen Cole Kleene, discípulo de Church y
responsable de importantes avances en la Lógica Matemática. Por otra parte, puede comprobarse
en forma directa que la clausura de un lenguaje junto con la operación de concatenación entre
cuerdas constituye una estructura algebraica conocida como monoide o semigrupo.

5
Curso de Informática III; Notas de Clase; Dr. Cyrano Ruiz Cabarrús, Ph.D.

Además, para toda cuerda w: wλ = λw = w

La concatenación es una operación claramente no conmutativa. El


orden de los “concatenandos” altera el resultado4.

2. La imagen inversa de una cuerda w, denotada como wR se explica de la


siguiente forma:

Si: w = a1a2...an, entonces: wR = an...a2a1

Además, para la cuerda nula, su imagen inversa es ella misma.

La versión recursiva de la definición de imagen inversa es la siguiente:

a. λR = λ
b. (wa)R = awR

Para toda cuerda w y para toda letra a del alfabeto. La primera parte
corresponde al caso base, la segunda, al paso inductivo.

3. El largo de una cuerda w, denotado por: |w|, es el número de letras que


contiene. Se define el largo de una cuerda en versión recursiva, de la
siguiente manera:

a. |λ| = 0
b. |aw| = |w| + 1

Para toda cuerda w y toda letra a del alfabeto. Nuevamente, la primera


parte corresponde al caso base, en tanto que la segunda al inductivo.

4. La concatenación de una cuerda consigo misma n veces se identifica como


una “potencia” de la cuerda, es decir, si w es una cuerda del alfabeto y n
es un número natural, wn es la cuerda que se obtiene al concatenar la
cuerda w consigo misma n veces, siendo el caso especial de que cualquier
cuerda “elevada” a la cero, es igual a la cuerda nula.

Una definición recursiva puede presentarse de la siguiente manera:

i. w0 = λ.
ii. Wn+1 = wnw

4
Sin embargo, la concatenación sí es una operación asociativa, cuyo elemento neutro
es la cuerda nula. Por esa razón, se indicó anteriormente que la clausura de Kleene,
junto con la concatenación constituyen una estructura algebraica conocida como
monoide o semi-grupo.

6
Curso de Informática III; Notas de Clase; Dr. Cyrano Ruiz Cabarrús, Ph.D.

5. Sea una cuerda w de un alfabeto dado. Se define como:

a. Un prefijo de w a una cuerda obtenida al quitar cero o más letras


finales de w.

b. Un sufijo de w a una cuerda obtenida al suprimir cero o más letras


iniciales de w.

c. Una subcuerda de w a una cuerda obtenida al remover un prefijo y


un sufijo de w. Nótese que todo prefijo y todo sufijo son subcuerdas
de w, pero no toda subcuerda es un prefijo o sufijo de w. También es
de notar que dada cualquier cuerda w, tanto w como la cuerda nula
son prefijos, sufijos y subcuerdas de sí misma.

d. Se dice que v es prefijo, sufijo o subcuerda propia de w si cumplen


con la definición respectiva pero además no son ni la cuerda nula ni
la misma cuerda w.

e. Una subsecuencia5 de w es una cuerda formada al “extirpar” cero o


más letras de w, no necesariamente contiguas.

LENGUAJES

En el contexto del presente libro, se define un lenguaje como un subconjunto de la


clausura de Kleene, el gran universo Σ* (incluyendo el conjunto vacío y el conjunto
cuyo único elemento es la cuerda nula, conjuntos diferentes).

La anterior definición es sencilla pero engañosamente amplia. Los lenguajes


pueden ser finitos o infinitos. Además, por el hecho de ser conjuntos, los lenguajes
pueden ser definidos en forma enumerativa, descriptiva o mediante métodos que
serán presentados en capítulos siguientes.

Debido a que los lenguajes son conjuntos en sí, se pueden definir las operaciones
de conjuntos usuales entre lenguajes. Cuando existe más de una operación entre
dos o más lenguajes, se establece una jerarquía u orden natural en la ejecución
de dichas operaciones. La potenciación tiene la mayor jerarquía, seguida de la
concatenación y la unión. Las operaciones entre paréntesis rompen cualquier
precedencia entre las operaciones.

5
El concepto de subsecuencia juega un papel importante en algoritmos genéticos en donde se
define la “proximidad” de dos fragmentos de genoma sobre la base de la Máxima Común
Subsecuencia (MCS) entre dos fragmentos genéticos. Existen algoritmos complejos pero muy
eficientes que calculan la MCS. El estudio de tales algoritmos cae fuera del alcance de este texto.

7
Curso de Informática III; Notas de Clase; Dr. Cyrano Ruiz Cabarrús, Ph.D.

Dados dos lenguajes L y M, se define:

1. La unión de ellos, escrita como: L U M (también denotado por: L + M) al


lenguaje formado por cuerdas que pertenecen al lenguaje L o bien al
lenguaje M.

L ∪ M = {w ∈ Σ* | w ∈ L o w ∈ M }

2. La concatenación de ellos, escrita como: LM, al lenguaje constituido por


cuerdas que se forman concatenando (como se definió en sección anterior)
una cuerda del lenguaje L con una cuerda de lenguaje M (en ese orden).

LM = {w ∈ Σ* | (∃x ∈ L) ∧ (∃y ∈ M ) ∋ w = xy}

3. Si n es un número natural, Ln se define como el lenguaje formado por el


lenguaje L concatenado consigo mismo n veces en el sentido de la
definición anterior. Si n es cero, el lenguaje resultante será el lenguaje cuyo
único elemento es la cuerda nula.

Ln = {w ∈ Σ* | ∃x ∈ L ∋ w = x n }

4. Otra manera de conceptuar la clausura de Kleene de un conjunto, en


particular la de un lenguaje, por ejemplo L, es definiéndola como la unión de
todas las “potencias” naturales de L, según la definición anterior. Se denota
esta clausura como L*.


L* = U Li
i =0

5. La clausura positiva L+ se define como la clausura de Kleene anterior, pero


excluyendo la cuerda nula.

L+ = L * −{λ}

6. Es interesante reiterar que el conjunto vacío y el conjunto cuyo único


elemento es la cuerda nula son ambos ejemplos válidos (aunque teóricos)
de lenguajes, pero distintos.

EJEMPLOS

1. Si Σ = { a, b}, entonces:

a. L = {aba, bbbaa, aaa} es un lenguaje (finito) del alfabeto

8
Curso de Informática III; Notas de Clase; Dr. Cyrano Ruiz Cabarrús, Ph.D.

b. L = {anbn; donde n es un número natural} es un lenguaje (infinito) del


alfabeto.

c. L = { w ∈ Σ* tal que |w| = 5 }, es el lenguaje de todas las cuerdas


cuya longitud es 5.

d. Ø el conjunto vacío es un lenguaje del alfabeto

e. Σ, el alfabeto mismo es un lenguaje

f. { λ } es un lenguaje cuyo único elemento es la cuerda nula

2. Si L = { A, B, C, ..., Z, a, b, c, ..., z } y D = { 0, 1, 2, ..., 9 }

a. L + D es el conjunto de palabras de longitud 1 (letras o dígitos)

b. LD es el conjunto de cuerdas que consisten en una letra seguida de


un dígito.

c. L4 es el conjunto de palabras que contienen exactamente 4 letras. Es


de notar que la definición permite palabras con letras repetidas.

d. L* es el conjunto de todas las palabras (de longitud arbitraria)


formadas únicamente por letras, incluyendo también la cuerda nula.

e. L(L+D)* es el conjunto de palabras que empiezan con una letra


seguida de cero o más letras o dígitos.

f. D+ es el conjunto de palabras con uno o más dígitos.

El segundo ejemplo es de particular interés puesto que da paso al concepto de


“expresiones regulares”, fundamental en el análisis léxico de compiladores,
tema que será tratado más adelante.

También podría gustarte