Sie sind auf Seite 1von 89

INSTITUTO NACIONAL DE MXICO

INSTITUTO TECNOLGICO DE ACAPULCO


Educacin Tecnolgica con Compromiso Social
Carrera:
Ingeniera en Sistemas Computacionales
Asignatura:
Lenguajes y Autmatas II
Actividades de Aprendizaje
Unidad 1. Analizador Semntico
COMPETENCIA ESPECIFICA

Disea mediante el uso de reglas semnticas dirigidas por sintaxis, un


analizador semntico para un compilador.
Profesor: Silvestre Bedolla Solano
Integrantes equipo 5
Nombre
Nmero de control
Solano Jurez Jess Brandon
De la Cruz lozano Edgar Moiss
Hernndez Barrera Arturo Orlando
flores olea Jess Margarito
Daz Carbajal Alberto

Acapulco Guerrero, 2 De septiembre 2016.

NDICE
1

Introduccin..3
Actividad 1 Detectar errores semnticos...7
Actividad 2 Disear y seleccionar informacin sobre la construccin de un
analizador semntico..10
Actividad 3 Reconocer el manejo de tipos en las expresiones y el uso de
operadores. ...................................................................................................13
Actividad 4 Establecer las reglas para la conversin de tipos (casting) en
expresiones. ..18
Actividad 5 Agregar acciones semnticas a la estructura de la gramtica.
...25
Actividad 6 Manipular la tabla de conversin de smbolos y de errores y
direcciones. ..26
Actividad 7 Integrar equipos de trabajo para la construccin de un analizador
semntico. 30 ..
Actividad 8 Propuesta de proyecto 82
Conclusin.84
Bibliografa 85

INTRODUCCIN
Antes de comenzar es necesario conocer algunos conceptos para poder
entender mejor el desarrollo del tema y se enlistan a continuacin:
Semntica: Conjunto de reglas que especifican el significado de cualquier
sentencia sintcticamente correcta y escrita en un determinado lenguaje.

Anlisis: Examen detallado de una cosa para conocer sus caractersticas o


cualidades, o su estado, y extraer conclusiones, que se realiza separando o
considerando por separado las partes que la constituyen.

La fase de anlisis semntico revisa el programa fuente para tratar de encontrar


errores semnticos y rene la informacin sobre los tipos para la fase posterior de
generacin de cdigo. En ella se utiliza la estructura jerrquica determinada por la
fase de anlisis sintctico para identificar los operadores y operandos de
expresiones y proposiciones.
Un componente importante del anlisis semntico es la verificacin de tipos. Aqu,
el compilador verifica si cada operador tiene operandos permitidos por la
especificacin del lenguaje fuente. Por ejemplo, las definiciones de muchos
lenguajes de programacin requieren que el compilador indique un error cada vez
que se use un nmero real como ndice de una matriz. Sin embargo, la
especificacin del lenguaje puede imponer restricciones a los operandos, por
ejemplo, cuando un operador aritmtico binario se aplica a un nmero entero y a
un nmero real. Revisa que los arreglos tengan definido el tamao correcto.
El analizador semntico se compone de un conjunto de rutinas independientes,
llamadas por los analizadores morfolgico y sintctico.
El anlisis semntico utiliza como entrada el rbol sintctico detectado por el
anlisis sintctico para comprobar restricciones de tipo y otras limitaciones
semnticas y preparar la generacin de cdigo.
En compiladores de un solo paso, las llamadas a las rutinas semnticas se
realizan directamente desde el analizador sintctico y son dichas rutinas las que
llaman al generador de cdigo. El instrumento ms utilizado para conseguirlo es la

gramtica de atributos. En compiladores de dos o ms pasos, el anlisis


semntico se realiza independientemente de la generacin de cdigo, pasndose
informacin a travs de un archivo intermedio, que normalmente contiene
informacin sobre el rbol sintctico en forma linealizada (para facilitar su manejo
y hacer posible su almacenamiento en memoria auxiliar).
En cualquier caso, las rutinas semnticas suelen hacer uso de una pila (la pila
semntica) que contiene la informacin semntica asociada a los operandos (y a
veces a los operadores) en forma de registros semnticos.
Existen dos formas de describir la semntica de un lenguaje de programacin:
mediante especificacin informal o natural y formal.
La descripcin informal de un lenguaje de programacin es llevada a cabo
mediante el lenguaje natural. Esto hace que la especificacin sea inteligible (en
principio) para cualquier persona. La experiencia nos dice que es una tarea muy
compleja, si no imposible, el describir todas las caractersticas de un lenguaje de
programacin de un modo preciso.
La descripcin formal de la semntica de lenguajes de programacin es la
descripcin rigurosa del significado o comportamiento de programas, lenguajes de
programacin, mquinas abstractas o incluso cualquier dispositivo hardware.

Revelar posibles ambigedades existentes implementaciones de


procesadores de lenguajes o en documentos descriptivos de lenguajes de
programacin.

Ser utilizados como base para la implementacin de procesadores de


lenguaje.

Verificar propiedades de programas en relacin con pruebas de correccin


o informacin relacionada con su ejecucin.

Disear nuevos lenguajes de programacin, permitiendo registrar


decisiones sobre construcciones particulares del lenguaje, as como permitir
descubrir posibles irregularidades u omisiones.

Facilitar la comprensin de los lenguajes por parte del programador y como


mecanismo de comunicacin entre diseador del lenguaje, implementador y
programador. La especificacin semntica de un lenguaje, como documento
de referencia, aclara el comportamiento del lenguaje y sus diversas
construcciones.

Estandarizar lenguajes mediante la publicacin de su semntica de un


modo no ambiguo. Los programas deben poder procesarse en otra
implementacin de procesador del mismo lenguaje exhibiendo el mismo
comportamiento.

VERIFICACION DE TIPOS DE EXPRESIONES

Formado por las definiciones y reglas que permiten comprobar el dominio


de un identificador, y en qu contextos puede ser usado.

Cada lenguaje tiene un sistema de tipos propio, aunque puede variar de


una a otra implementacin.

La comprobacin de tipos es parte del anlisis semntico.

Funciones Principales:

Reglas de un lenguaje que permiten asignar tipos a las distintas partes


de un programa y verificar su correccin.

Inferencia de tipos: calcular y mantener la informacin sobre los tipos de


datos.

Verificacin de tipo: asegurar que las partes de un programa tienen


sentido segn las reglas de tipo del lenguaje.

Todos los lenguajes permiten crear nuevos tipos complejos a partir de


otros ms simples mediante constructores de tipos:

Matrices, productos, registros, punteros, funciones,

En Pascal: array, set, record,...

En C++: struct, class, union,....

Para analizar los diferentes tipos que intervienen dentro de un programa, el


compilador debe contar con una estructura interna que le permita manejar
cmodamente las expresiones de tipos.

Esta estructura interna:

Debe ser fcilmente manipulable, pues su creacin se realizar conforme


se hace la lectura del programa fuente.

Debe permitir comparar fcilmente las expresiones asignadas a distintos


trozos de cdigo, especialmente a los identificadores de variables.

La forma ms habitual de representacin son los grafos a cclicos


dirigidos (GADs).

La ventaja de estas representaciones es que ocupan poca memoria y por


tanto la comprobacin de equivalencia se efecta con rapidez.

ACTIVIDAD 1. DERECTAR ERRORES SEMNTICOS

RECUPERACION DE ERRORES
Un sistema de tipos seguro elimina la necesidad de comprobar dinmicamente
errores de tipos ya que permite determinar estticamente que dichos errores no
pueden ocurrir cuando se est ejecutando el programa objeto. Se dice que un
lenguaje es fuertemente tipificado si su compilador puede garantizar que los
programas que acepte se ejecutarn sin errores de tipo.

MANEJO DE ERRORES
Es una de las misiones ms importantes del compilador. Se utiliza ms en el
anlisis, pero los errores pueden darse en cualquier fase. El manejo de errores es
una tarea difcil por dos motivos:

A veces algunos errores ocultan otros.

Un error puede provocar una avalancha de errores que se solucionan


con el primero.

CRITERIOS A SEGUIR PARA EL MANEJO DE ERRORES

Pararse al detectar el primer error (conveniente para un compilador


interactivo).

Detectar todos los errores de una pasada (conveniente para un


compilador de lnea).

CAPTURAS DE TRES EJEMPLOS: Un archivo de texto con Operaciones


Aritmticas.

Al momento de ingresar un archivo.txt, en analizador semntico se encarga de realizar


un anlisis para poder identificar el contento del archivo, muestra en la pantalla una
ventana especificando que tipo de token es.

EJEMPLO 2: Uso de Variables (Int, string)

Una vez identificado el token, en la parte derecha se crea una tabla de smbolos
ordenando el tipo de dato que contiene el archivo de texto.
8

EJEMPLO 3: Uso de condiciones (Bool)

En dado caso de que el archivo contenga errores, mostrar la lnea en donde se encuentra el error,
este compilador, tiene como funciones, abrir, guardar e incluso modificar. Se agregan propiedades
como cambiar el color del texto, tamao de la ventana como tambin una opcin de Ayuda.

ACTIVIDAD 2. DISEAR Y SELECCIONAR INFORMACION


CONSTRUCCION DE UN ANALIZADOR SEMANTICO.

SOBRE

LA

Los rboles de expresiones representan el cdigo de nivel del lenguaje en forma de


datos. Los datos se almacenan en una estructura con forma de rbol. Cada nodo
del rbol de expresin representa una expresin, por ejemplo, una llamada al
mtodo o una operacin binaria, como x < y.

Un rbol de expresin sirve para evaluar expresiones del tipo:


(a + b)*c/d Para que un rbol represente una expresin se deben tomar en cuenta
2 caractersticas muy importantes:

Cualquier hoja est etiquetada slo con un operando.

Cualquier nodo interior n est etiquetada por un operador.

Al introducir la expresin debemos de tomar en cuenta las siguientes


caractersticas:

La raz siempre debe ser un operador

Las hojas siempre deben ser operandos

Los nodos deben estar etiquetados por operadores Si un operador tiene mayor
prioridad que la raz se coloca como hijo.

Si un operador tiene igual o menor prioridad que un nodo se coloca como padre.

Un nodo puede contener como hijo otro subrbol que contiene una pequea
expresin.

En los rboles de expresin, la sucesin del preorden de etiquetas nos da lo que se


conoce como la forma prefijo de una expresin Anlogamente, la sucesin
postorden de las etiquetas de un rbol expresin nos da lo que se conoce como la
representacin postfijo de una expresin Finalmente, el orden de una expresin en
un rbol de expresin nos da la expresin infijo en s misma, pero sin parntesis
Construccin de un rbol de expresin Algoritmo:

10

Mientras carcter diferente de nulo

Leer carcter de la lista

Si es parntesis pasar al siguiente carcter

Crear un nodo nuevo que contenga ese carcter Operando

Si el rbol est vaco hacer raz a nuevo, si no recorrer el rbol por la


derecha hasta llegar a un nodo con hojas, si la hoja izquierda, no est
etiquetada colocar operando, si no colocarlo en la hoja derecha. Operador

Si la raz es un operando, insertar nuevo en ese nodo, y convertir el


operando en el hijo izquierdo, si no si hay un parntesis abierto insertar
nuevo en la ltima hoja derecha y colocar operando como hijo izquierdo.

Si el carcter anterior es parntesis izquierdo si el siguiente carcter es


parntesis derecho si solo hay un operador en el rbol nuevo se convierte
en raz, si no se inserta en el ltimo nodo derecho, y el nodo se convierte en
hijo izquierdo.

Si no se cumple ninguna de las condiciones anteriores si la raz es de igual


prioridad o menor prioridad convertir la raz en el hijo izq. de nuevo si no la
prioridad del nodo raz es mayor al de nuevo insertar nuevo como hijo
derecho y colocar el nodo reemplazado como hijo izquierdo.

Construccin
Para construir los 3 rboles, debemos comenzar por definir qu elementos emplearemos para
cada estructura:

11

Fjate que el rbol resultante puede representar programas en diversos lenguajes de


programacin del estilo C, Pascal, etc. Ahora debemos utilizar los atributos para construir el
rbol. Utilizando el atributo arb para devolver el rbol que construye cada no terminal, podemos
hacer algo parecido a:

Para la implementacin hay dos opciones principales:


Utilizar funciones (NodoSi, NodoMientras,. . .) que devuelvan una estructura de datos
adecuada.
Utilizar objetos (NodoSi, NodoMientras,. . .) para cada uno de los nodos.
Probablemente, la segunda opcin sea la ms cmoda para el trabajo posterior con el rbol.
En cuanto a la lista de sentencias, podemos utilizar nodos que tengan un grado variable, para
eso almacenamos una lista con los hijos:

12

EJEMPLOS
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Text.RegularExpressions;
namespace cadena_expresion
{
class Program
{
static void Main(string[] args)
{
analizaFichero();
}
static public void analizaFichero()
{
string[] Cadenas= {"Aplastar","Haragan","Encargado","Seleccion"};
string sexpresion;
Console.Write("Escribir expresion: ");
sexpresion = Console.ReadLine();
foreach (string s in Cadenas)

13

{
//System.Console.Write("{0,24}", s);
if (Regex.IsMatch(s, sexpresion))
{
System.Console.WriteLine("Existe coincidencia '{0}' en: '{1}'", sexpresion, s);
}
else
{
System.Console.WriteLine("No existe coincidencia '{0}' en: '{1}'", sexpresion, s);
}

Console.ReadLine();
}
}
}

}
Ejemplo 1:

En este primer ejemplo, se toman 4 palabras en las cuales mediante un


reconocimiento, el programa indica si la vocal a se encuentra en las cadenas
predefinidas, de no existe coincidencia como en el caso de la cuarta cadena, se
nos indicara que no existe coincidencia de dicha expresin en la cadena.
Ejemplo 2:

14

En este caso la expresin no obtuvo coincidencia en ninguna de las cadenas.


Ejemplo 3:

En este caso la expresin o fue hallada en dos de tres cadenas.


ACTIVIDAD 3: RECONOCER EL MANEJO DE TIPO EN LAS EXPRESIONES Y
EL USO DE OPERADORES
Una expresin es una combinacin de operadores y operandos de cuya
evaluacin se obtiene un valor. Los operandos pueden ser nombres que denoten
objetos variables o constantes, funciones, literales de cualquier tipo adecuado de
acuerdo con los operadores u otras expresiones ms simples. La evaluacin de
una expresin da lugar a un valor de algn tipo, una expresin se dice que es del
tipo de su resultado.
Expresiones
Una expresin es una instruccin o sentencia que devuelve un valor llamado valor de retorno y
que asigna a una variable un

Dato numrico

Valor lgico

Carcter
15

Cadena de caracteres o dato textual

Ejemplo 1:

Ejemplo 2:

Operadores
Un operador permite relacionar dos datos en una expresin y evaluar el resultado de una
operacin.
Tipos:

Aritmticos

De asignacin

De comparacin

Lgicos

ARITMTICOS
Manipulan datos numricos. Son los siguientes:

Suma +

Resta -

Producto *

Divisin /

Resto de la divisin entera o mdulo %

16

Incremento unitario ++

Decremento unitario -

Incremento de cien en cien +=100

Decremento de cien en cien -=100

Ejemplo 1: muestra por consola una serie de resultados asociados a clculos sencillos
realizados
con
los
operadores
aritmticos.

DE ASIGNACIN
Transfieren datos de una variable a otra. Son los siguientes:

x+=y

x=x+y

x-=y

x=x-y

x*=y

x=x*y

x/=y

x=x/y

x%=y

x=x%y

Es el mdulo o resto de una divisin

Ejemplo 1:

Valor de z: 8

17

DE COMPARACIN
Comparan dos datos y devuelven un valor booleano. Son los siguientes:

==

igual (no confundir con el = de asignacin)

!=

distinto

<

mayor que

<

menor que

>=

mayor o igual que

<=

menor o igual que

Ejemplo:

Valor de z: true

LGICOS
Concatenan expresiones lgicas con objeto de evaluar si es cierto o falso el conjunto de las
expresiones. Son los siguientes:

&& (Y lgico): si todas las expresiones lgicas que se evalan son verdaderas se
devuelve un valor booleano true; si alguna es falsa, devuelve false.

|| (O lgico): si alguna de las expresiones lgicas que se evala es verdadera, se


devuelve un valor booleano true; si todas son falsas, devuelve false.

! (NOT): invierte el valor de una expresin booleana.

Ejemplo 1:

18

Valor de z: true

EJEMPLO 1: muestras las operaciones que se ejecutan como los operadores


aritmticos y ejecuta la operacin

EJEMPLO 2: Evala la expresin identifica cada uno de los operadores de la


expresin y verifica que no tenga errores.

19

EJEMPLO 3: ejecuta las operaciones de acuerdo a los valores que tiene las
variables declaradas y muestra los resultados

ACTIVIDAD 4. ESTABLECER LAS REGLAS PARA LA CONVERSIN DE TIPOS


(CASTING) EN EXPRESIONES.

20

Quizs te hayas preguntado qu pasa cuando escribimos expresiones numricas


en las que no todos los operandos son del mismo tipo. Por ejemplo:
char n;
int a, b, c, d;
float r, s, t;
...
a = 10;
b = 100;
r = 1000;
c = a + b;
s = r + a;
d = r + b;
d = n + a + r;
t=r+as
+ c;
...
En estos casos, cuando los operandos de cada operacin binaria asociados a un
operador son de distinto tipo, el compilador los convierte a un tipo comn. Existen
reglas que rigen estas conversiones, y aunque pueden cambiar ligeramente de un
compilador a otro, en general sern ms o menos as:
Cualquier tipo entero pequeo como char o short es convertido a int o unsigned
int. En este punto cualquier pareja de operandos ser int (con o sin signo), long,
long long, double, float o long double.
Si un operando es de tipo long double, el otro se convertir a long double.
Si un operando es de tipo double, el otro se convertir a double.
Si un operando es de tipo float, el otro se convertir a float.
Si un operando es de tipo unsigned long long, el otro se convertir a unsigned long
long.
Si un operando es de tipo long long, el otro se convertir a long long.

21

Si un operando es de tipo unsigned long, el otro se convertir a unsigned long.


Si un operando es de tipo long, el otro se convertir a long.
Si un operando es de tipo unsigned int, el otro se convertir a unsigned int.
Llegados a este punto ambos operandos son int.
Veamos ahora el ejemplo:
c = a + b; caso 10, ambas son int.
s = r + a; caso 4, a se convierte a float.
d = r + b; caso 4, b se convierte a float.
d = n + a + r; caso 1, n se convierte a int, la operacin resultante corresponde al
caso 4, el resultado (n+a) se convierte a float.
t = r + a s + c; caso 4, a se convierte a float, caso 4 (r+a) y s son float, caso 4, c se
convierte a float.
Tambin se aplica conversin de tipos en las asignaciones, cuando la variable
receptora es de distinto tipo que el resultado de la expresin de la derecha.
En el caso de las asignaciones, cuando la conversin no implica prdida de
precisin, se aplican las mismas reglas que para los operandos, estas
conversiones se conocen tambin como promocin de tipos. Cuando hay prdida
de precisin, las conversiones se conocen como democin de tipos. El compilador
normalmente emite un aviso o warning, cuando se hace una democin implcita,
es decir cuando hay una democin automtica.
En el caso de los ejemplos 3 y 4, es eso precisamente lo que ocurre, ya que
estamos asignando expresiones de tipo float a variables de tipo int.
Conversiones a bool
^
En C++ podemos hablar de otro tipo de conversin de tipo implcita, que se realiza
cuando se usa cualquier expresin entera en una condicin, y ms generalmente,
cuando se usa cualquier expresin donde se espera una expresin booleana.
El dominio del tipo bool es muy limitado, ya que slo puede tomar dos valores: true
y false.
Por convenio se considera que el valor cero es false, y cualquier otro valor entero
es true.
22

Por lo tanto, hay una conversin implcita entre cualquier entero y el tipo bool, y si
aadimos esta regla a las explicadas antes, cualquier valor double, long double,
float o cualquiera de los enteros, incluso char, se puede convertir a bool.
Esto nos permite usar condiciones abreviadas en sentencias if, for, while o
do..while,
cuando el valor a comparar es cero.
Por ejemplo, las siguientes expresiones booleanas son equivalentes:
0 == x equivale a !x.
0 != x equivale a x.
En el primer caso, usamos el operador == para comparar el valor de x con cero,
pero al aplicar el operador ! directamente a x obligamos al compilador a
reinterpretar su valor como un bool, de modo que si x vale 0 el valor es false, y !
false es true. De forma simtrica, si x es distinto de cero, se interpretar como
true, y !true es false. El resultado es el mismo que usando la expresin 0 == x.
En el segundo caso pasa algo anlogo. Ahora usamos el operador != para
comparar el valor de x tambin con cero, pero ahora interpretamos directamente x
como bool, de modo que si x vale 0 el valor es false, y si x es distinto de cero, se
interpretar como true. El resultado es el mismo que usando la expresin 0 != x.
No est claro cul de las dos opciones es ms eficaz, a la hora de compilar el
programa.
Probablemente, la segunda requiera menos instrucciones del procesador, ya que
existen instrucciones de ensamblador especficas para comparar un entero con
cero. Del otro modo estaremos comparando con un valor literal, y salvo que el
compilador optimice este cdigo, generalmente se requerirn ms instrucciones de
este modo.
Aadir que los ejemplos anteriores funcionan, aunque el tipo de x no sea un
entero. Si se trata de un valor en coma flotante se realizar una conversin
implcita a entero antes de evaluar la expresin.
Casting: conversiones explcitas de tipo
^
Para eludir estos avisos del compilador se usa el casting, o conversin explcita.
Nota: de nuevo nos encontramos ante un trmino que suele aparecer en ingls en
los documentos. Se podra traducir como amoldar o moldear, pero no se hace.

23

Tambin es un trmino que se usa en cine y teatro, y se aplica al proceso de


asignar papeles a los actores.
La idea es anloga, en el caso de las variables, asignamos papeles a los valores,
segn sus caractersticas. Por ejemplo, para convertir el valor en coma flotante
14.232 a entero se usa el valor 14, podramos decir que 14 est haciendo el papel
de 14.232 en la representacin.
O que se ajusta a un molde o troquel: lo que sobra se elimina.
En general, el uso de casting es obligatorio cuando se hacen asignaciones, o
cuando se pasan argumentos a funciones con prdida de precisin. En el caso de
los argumentos pasados a funciones es tambin muy recomendable, aunque no
haya prdida de precisin.
Eliminar los avisos del compilador demostrar que sabemos lo que hacemos con
nuestras variables, aun cuando estemos haciendo conversiones de tipo extraas.
En C++ hay varios tipos diferentes de casting, pero de momento veremos slo el
que existe tambin en C.
Un casting tiene una de las siguientes sintaxis:
(<nombre de tipo>)<expresin>
<nombre de tipo>(<expresin>)
Esta ltima es conocida como notacin funcional, ya que tiene la forma de una
llamada a funcin.
En el ejemplo anterior, las lneas 3 y 4 quedaran:
d = (int)(r + b);
d = (int)(n + a + r);
O bien:
d = int(r + b);
d = int(n + a + r);
Hacer un casting indica que sabemos que el resultado de estas operaciones no es
un int, que la variable receptora s lo es, y que lo que hacemos lo estamos
haciendo a propsito.
Ejemplo 1:
Tabla->Cells[0][0]="Token";
24

Tabla->Cells[1][0]="Tipo";
TablaTokens->Cells[0][0]="Tokens";
FILE *Tabla1, *Tabla2;
int i=1;
int j=1;
Tabla1=fopen("c:/Analisis.Txt", "r");
fread(&lex1,sizeof(lex1),1,Tabla1);
while (!feof(Tabla1))
{
Tabla->Cells[0][i]=lex1.token;
Tabla->Cells[1][i++]=lex1.tipo;
fread(&lex1,sizeof(lex1),1,Tabla1);
}
fclose(Tabla1);
Tabla2=fopen("c:/Tokens.Txt", "r");
fread(&token2,sizeof(token2),1,Tabla2);
while (!feof(Tabla2))
{
TablaTokens->Cells[0][j]=token2.tokens;
fread(&token2,sizeof(token2),1,Tabla2);

25

En el ejemplo de nuestra captura se observa como se hace la conversin de


expresiones de tipo numricas indicando cado uno de los smbolos y expresiones
introducidas mediante un anlisis sintctico este programa fue desarrollado en el
lenguaje de programacin C++.
Ejemplo 2:
Console.WriteLine(" ")
Console.WriteLine("============================= ANALIZADOR DE
UNA EXPRESION LEXICA-SINTACTICA ===========================")
Console.WriteLine(" ")
Console.WriteLine("Ingrese una expresion aritmtica, lgica, relacional o exponencial.")
Console.WriteLine(" ")
Console.Write("Ingrese la expresin : ")
Console.Write(" ")
Dim myString As String = Console.ReadLine
Console.WriteLine(" ")
Dim myChar As String
Dim TestLen As Integer = Len(myString)
Dim exp(TestLen) As String
Dim i As Integer
Dim J As Integer
Console.WriteLine("ANALIZADOR LEXICO: ")
'AQUI NOS HACE REFERENCIA A LOS CARACTERES RECONOCIDOS'
Console.WriteLine("
COMPONENTES LEXICOS RECONOCIDOS: ")
Console.Write("
")
For i = 0 To (TestLen - 1)
myChar = myString.Chars(i)
If myChar = "+" Or myChar = "-" Or myChar = "/" Or myChar = "*" Or myChar =
"=" Or myChar = "^" Then

26

exp(i) = "op"
Console.Write("<" & exp(i) & "," & myChar & ">")
ElseIf myChar = "a" Or myChar = "b" Or myChar = "c" Or myChar = "d" Or myChar
= "e" Or myChar = "f" Or myChar = "g" Or myChar = "h" Or myChar = "i" Or myChar = "j"
Or myChar = "k" Or myChar = "l" Then
exp(i) = "exp"
Console.Write("<" & exp(i) & "," & myChar & ">")
ElseIf myChar = "1" Or myChar = "2" Or myChar = "3" Or myChar = "4" Or myChar
= "5" Or myChar = "6" Or myChar = "7" Or myChar = "8" Or myChar = "9" Then
exp(i) = "num"
Console.Write("<" & exp(i) & "," & myChar & ">")
ElseIf myChar = "(" Then
exp(i) = "par_d"
Console.Write("<" & exp(i) & "," & myChar & ">")
ElseIf myChar = ")" Then
exp(i) = "par_iz"
Console.Write("<" & exp(i) & "," & myChar & ">")
Else
Console.WriteLine(myChar & "
End If
Next
Console.WriteLine(" ")
Dim z As Integer
J=0
z=1

COMPONENTE LEXICO NO RECONOCIDO ")

En el ejemplo de nuestra captura se observa como se hace la conversin de


expresiones de tipo numricas indicando cado uno de los smbolos y expresiones
introducidas mediante un anlisis sintctico adems muestra si la expresin
introducida contiene errores semnticos y si son o no reconocidos este programa
es desarrollado en el lenguaje de programacin c#.
Ejemplo 3:
private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {
27

oAnaLex.Inicia();
oAnaLex.Analiza(jTextArea1.getText());
modelo=new ModeloDeTabla(oAnaLex.Tokens(),oAnaLex.Lexemas());
jTable1.setModel(modelo);
}
private void jButton2ActionPerformed(java.awt.event.ActionEvent evt) {
jTextArea1.setText("");
}
public static void main(String args[]) {
java.awt.EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
new AnaLex().setVisible(true);
}
});
}

28

En el ejemplo de nuestra captura se observa como se hace la conversin de


expresiones de tipo numricas indicando cado uno de los tokens y expresiones
introducidas mediante un anlisis lxico adems muestra si la expresin
introducida muestra cada expresin reconocida este programa es desarrollado en
el lenguaje de programacin java.

29

ACTIVIDAD 5: AGREGAR ACCIONES SEMANTICAS A LA ESTRUCTURA DE


LA GRAMATICA
Es la fase del analizador que se encarga de chequear el texto de entrada en base
a una gramtica dada. Y en caso de que el programa de entrada sea vlido,
suministra el rbol sintctico que lo reconoce.
La Gramtica es el estudio de las reglas y principios que regulan el uso del
lenguaje a nivel intraoracional. Tambin se denomina as al conjunto de reglas y
principios que gobiernan el uso de un lenguaje determinado, por lo que puede
decirse que cada lenguaje tiene su propia gramtica.
En teora, se supone que la salida del analizador sintctico es alguna
representacin del rbol sintctico que reconoce la secuencia de Token
suministrada por el analizador lxico.
En la prctica, el analizador sintctico tambin hace:

Acceder a la tabla de smbolos (para hacer parte del trabajo del analizador
semntico).
Chequeo de tipos (del analizador semntico).
Generar cdigo intermedio.
Generar errores cuando se producen.
En definitiva, realiza casi todas las operaciones de la compilacin. Este
mtodo de trabajo da lugar a los mtodos de compilacin dirigidos por
sintaxis

Semntica de un lenguaje dar sentido a sus construcciones, como los tokens


estructura y sintaxis. Semntica ayudan a interpretar los smbolos, sus tipos y sus
relaciones con los dems. Anlisis semntico los jueces si la sintaxis estructura
construida en el programa de origen se deriva el significado o no.

int a = value;
No debe emitir un error lxico y la sintaxis en fase de anlisis, ya que es lxico y
estructuralmente correcto, pero se debe generar un error semntico como del tipo
de asignacin es diferente. Estas normas estn definidas por la gramtica de la
lengua y evaluado en anlisis semntico. Las siguientes tareas deben realizarse
en anlisis semntico:

30

Resolucin de mbito

Comprobacin de tipos

Matriz de control

Errores semnticos
Hemos mencionado algunos de los errores que la semntica analizador
semntico se espera para reconocer:

No coinciden los tipos

Variable no declarada

Identificador reservado uso indebido.

Declaracin de variables mltiples en un mbito.

Acceder a una variable fuera de alcance.

Parmetro formal y real no coincide.

31

EJEMPLO 1

Ilustracin 1: Ejemplo 1, cdigo

En la ilustracin 1 se define una variable a de tipo entero despus se le asigna un valor decimal y
una cadena porque nos muestra error

Ilustracin 2: Ejemplo 1 asignacin incorrecta

32

EJEMPLO 2

Ilustracin 3: Cdigo

En la ilustracin a una variable a se trata de asignar valores y esto da un error porque la variable
no est defina

Ilustracin 4: Muestra que hay un erro de semantica

33

EJEMPLO 3

Ilustracin 5: Ejemplo 2 errores de


definicin

Ilustracin 6: Cdigo

En la ilustracin se define una variable y se le asigna un tipo de dato diferente

Ilustracin 7:El codigo aceptado

34

EJEMPLOS
En la ilustracin 1 se define una variable a de tipo entero despus se le asigna un valor decimal y
una cadena porque nos muestra error

Ilustracin 8: Ejemplo 1 asignacin incorrecta

35

ACTIVIDAD 6. MANIPULAR LA TABLA DE CONVERSIN DE SMBOLOS Y DE


ERRORES Y DIRECCIONES
Una tabla de smbolos es una estructura de datos que usa el proceso de
traduccin de un lenguaje de programacin, por un compilador o un intrprete,
donde cada smbolo en el cdigo fuente de un programa est asociado con
informacin tal como la ubicacin, el tipo de datos y el mbito de cada variable,
constante o procedimiento.
Una implementacin comn de una tabla de smbolos puede ser una tabla hash, la
cual ser mantenida a lo largo de todas las fases del proceso de compilacin de
ticses.
Puede tratarse como una estructura transitoria o voltil, que sea utilizada
nicamente en el proceso de traduccin de un lenguaje de programacin, para
luego ser descartada, o integrada en la salida del proceso de compilacin para
una explotacin posterior, como puede ser, por ejemplo, durante una sesin
de depuracin, o como recurso para obtener un informe de diagnstico durante o
despus la ejecucin de un programa.
Los smbolos en la tabla de smbolos pueden referirse a constantes, a funciones o
a tipos de datos en el cdigo fuente de un programa.
La tabla de smbolos forma parte de cada fichero que contiene el cdigo
objeto durante el enlazado o linking de los diferentes ficheros; recae en la
responsabilidad del linker o enlazador resolver cualquier referencia no resuelta.
Los smbolos se guardan en la tabla con su nombre y una serie de atributos
opcionales que dependern del lenguaje y de los objetivos del procesador, este
conjunto de atributos almacenados se denomina registro de la tabla de smbolos.
Nombre del identificador.
Direccin en tiempo de ejecucin a partir del cual se almacenar el
identificador si es una variable.
Tipo del identificador. Si es una funcin, el tipo que devuelve la funcin.
Nmero de dimensiones del array (arreglo), o nmero de miembros de una
estructura o clase, o nmeros de parmetros si se trata de una funcin.
36

Tamao mximo o rango de cada una de las dimensiones de los array, si tiene
dimensin esttica.

Los errores que puede detectar el analizador sintctico son aquellos que violan las
reglas de una gramtica independiente del contexto. Ya hemos mencionado que
algunas de las caractersticas de un lenguaje de programacin no pueden
enunciarse con reglas independientes del contexto, ya que dependen de l; por
ejemplo, la restriccin de que los identificadores deben declararse previamente.
Un compilador utiliza una tabla de smbolos para llevar un registro de la
informacin sobre el mbito y el enlace de los nombres. Se examina la tabla de
smbolos cada vez que se encuentra un nombre en el texto fuente. Si se descubre
un nombre nuevo o nueva informacin sobre un nombre ya existente, se producen
cambios en la tabla.
Un mecanismo de tabla de smbolos debe permitir aadir entradas nuevas y
encontrar las entradas existentes eficientemente. Los dos mecanismos para tablas
de smbolos presentadas en esta seccin son listas lioeal.es y tablas de
dispersin. Cada esquema se evala basndose en el tiempo necesario para
aadir n entradas y realizar e consultas. Una lista lineal es lo ms fcil de
implantar, pero su rendimiento es pobre cuando e y n s vuelven ms grandes.
Los esquemas de dispersin proporcionan un mayor rendimiento con un esfuerzo
algo mayor de programacin y gasto de espacio. Ambos mecanismos pueden
adaptarse rpidamente para funcionar con la regla del anidamiento ms cercano.
La entrada misma de la tabla de smbolos puede establecerse cuando se aclara el
papel de un nombre y se llenan los valores de los atributos cuando se dispone de
la informacin. En algunos casos, el analizador lxico puede iniciar la entrada en
cuanto aparezca un nombre en los datos de entrada. A menudo, un nombre puede
indicar varios objetos distintos, quizs incluso en el mismo bloque o procedimiento
Los atributos de un nombre se introducen en respuesta a las declaraciones, que
pueden ser implcitas. Las etiquetas son a menudo identificadores seguidos de
dos puntos, as que una accin asociada con el reconocimiento de dicho
identificador puede ser introducir este hecho en la tabla de smbolos. Asimismo, la
sintaxis de las declaraciones de procedimientos especifica que algunos
identificadores son parmetros formales.

37

38

Ejemplo

%}

Package analizador;

%%

import static analizador.Token.*;

{WHITE} {/*Ignore*/}

%%

"=" {return ASSIGN;}

%class Lexer

"+" {return SUMA;}

%type Token

"*" {return MULT;}

L = [a-zA-Z_]

"-" {return RESTA;}

D = [0-9]

"/" {return DIV;}

WHITE=[ \t\r\n]

{L}({L}|{D})*
ID;}

%{

{lexeme=yytext();

("(-"{D}+")")|{D}+
return INT;}

public String lexeme;

. {return ERROR;}

39

return

{lexeme=yytext();

Ejemplo 1
Aqu nos muestra el ejemplo que hemos realizado, para saber si es correcto le
damos en la accin (compilar) y en la parte de abajo muestra que se compilo con
xito e indica el nmero de filas contadas

Ejemplo 2
Ya que compilo con xito mostraremos la tabla de tokens de dicho ejemplo

Ejemplo 3
A continuacin, mostraremos un error para indicar si los marca, le quitaremos el
punto y coma de la lnea 7 y sale el mensaje de error

ACTIVIDAD 7. INTEGRAR EQUIPOS PARA LA CONSTRUCCION DE UN ANALIZADOR


SEMANTICO.

PROGRAMA: ANALIZADOR SEMANTICO ELABORADO EN MICROSFT VISUAL C# 2013

DISEO DEL ANALIZADOR SEMANTICO

UTILIZANDO UN ARCHIVO.TXT PARA OBSERVAR EL PROCESO DE


DESARROLLO

CDIGO FUENTE

MANEJO DE ERRORES
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace ManejoDeErrores
{
public class TE
{

//Tabla errores (nmero de lnea, error, como solucionarlo)


public List<Tabla_Errores> TErrores = new List<Tabla_Errores>();
public List<Tabla_Errores> TErroresed = new List<Tabla_Errores>();
public List<Tabla_Errores> TablaErrores
{
get { return TErrores; }
set { TErrores = value; }
}
public void reinicialista()
{
TErrores.Clear();
TErroresed.Clear();
}
public void inicialestaE(){

Tabla_Errores te = new Tabla_Errores(0, "valor incorrecto",


"escriba el valor aceptado por el tipo de variable", "valor diferente al
aceptado por el tipo");
TErrores.Add(te);

Tabla_Errores te1 = new Tabla_Errores(1, "se espera un valor",


"escriba un valor para la variable ", "se espera un valor despues de...");
TErrores.Add(te1);

Tabla_Errores te2 = new Tabla_Errores(2, "error al abrir", "revise la


extencion del archivo o la direccion del mismo", "error al abrir el
archivo");
TErrores.Add(te2);

Tabla_Errores te3 = new Tabla_Errores(3, "error aritmetico",


"revise la operacin que esta realizando", "excepciones producidas
durante operaciones aritmticas");
TErrores.Add(te3);

Tabla_Errores te4 = new Tabla_Errores(4, "error dividir por cero ",


"escoja otro numero que no sea el 0 para dividir", "posible incongruencia
en divicion,o en cualquier operacin");
TErrores.Add(te4);

Tabla_Errores te5 = new Tabla_Errores(5, "error de conversion de


tipo", "verifique que los tipos de las variables sea el mismo ", "Se
produce cuando tiene lugar un error en tiempo de ejecucin en una
conversin explcita de un tipo base a una interfaz o a un tipo
derivado.");
TErrores.Add(te5);

Tabla_Errores te6 = new Tabla_Errores(6, "error referencia nula",


"revise que esta dando un valor ala variable", "Se produce al intentar
hacer referencia a un objeto cuyo valor es null.");
TErrores.Add(te6);

Tabla_Errores te7 = new Tabla_Errores(7, "error de


desbordamiento", "asegurese del tamao del resultado ", "Se produce
cuando una operacin aritmtica en un contexto produce un
desbordamiento.");
TErrores.Add(te7);
Tabla_Errores te8 = new Tabla_Errores(8, "error de Ambito",
"asegurese de que las llaves '{' tengan su contraparte '}' ", "Se produce
cuando hay alguna llave sin cerrar, ambito incompleto");
TErrores.Add(te8);
Tabla_Errores te9 = new Tabla_Errores(9, "sintaxis desconocida",
"asegurese de que la sintaxis sea correcta ", "Se produce cuando se
desconoce la sintaxis de la sentencia");
TErrores.Add(te9);
Tabla_Errores te10 = new Tabla_Errores(10, "sintaxis erronea",
"asegurese de que la sintaxis sea correcta, verifique espacios ", "Se
produce cuando la sintaxis de la sentencia contiene algun error");
TErrores.Add(te10);
Tabla_Errores te11 = new Tabla_Errores(11, "warning", "asegurese
de que las variables no esten repetidas ", "Se produce cuando mas de
una variable estan inicializadas con el mismo nombre");
TErrores.Add(te11);
}
public List<Tabla_Errores> llamatablaE()
{
return TErroresed;
}

public void addliste(int id,int nl)


{
foreach (var error in TErrores)
{
if (error.Id == id)
{
Tabla_Errores er = new Tabla_Errores();
er.Descripcion = error.Descripcion;
er.Solucion = error.Solucion;
er.Error = error.Error;
er.NumerodeLinea = nl;
TErroresed.Add(er);
}
}
}
public void addliste(int id)
{ foreach (var error in TErrores)
{

if (error.Id == id)
{
Tabla_Errores er = new Tabla_Errores();
er.Descripcion = error.Descripcion;
er.Solucion = error.Solucion;
er.Id = error.Id;
TErroresed.Add(er);
}

}
}
}
DESARROLLO DEL PROGRAMA
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.IO;
using Tsimbolos;
using System.Text.RegularExpressions;//using necesario , llama ala
referencia de la libreria de expresiones regulares
using Microsoft.Office.Interop.Excel;
using ManejoDeErrores;

namespace CompEd
{
public partial class Ide : Form
{
int cantLineas =0 ;

string nomarchivox;
TS tabla_simbolos = new TS();
TE tabla_errorres = new TE();

public Ide()
{
InitializeComponent();
}
private void salirToolStripMenuItem_Click(object sender, EventArgs
e)
{
System.Windows.Forms.Application.Exit();
}
private void toolStripButton1_Click(object sender, EventArgs e)
{
//AnlzdrSntctc();

}
private void toolStripButton7_Click(object sender, EventArgs e) {
System.Windows.Forms.Application.Exit();
}

private void Ide_Load(object sender, EventArgs e)//--------------{

tabla_errorres.inicialestaE();
tabla_simbolos.inicialista();
tabControl1.Visible = false;

PagCodigo.Select();
PagCodigo.DetectUrls = true;
#region area de notificacion
notifyIcon1.Text = " CompEd# 2013";
notifyIcon1.BalloonTipTitle = " <# Hello World";
notifyIcon1.BalloonTipText = "Bienvenido a CompEd# 2013";
notifyIcon1.BalloonTipIcon = ToolTipIcon.Info;
this.Click += new EventHandler(notifyIcon1_Click);

notifyIcon1.Visible = true;
notifyIcon1.ShowBalloonTip(3000);
#endregion
}

private void notifyIcon1_Click(object sender, EventArgs e)


{
if (this.WindowState == FormWindowState.Minimized)
this.WindowState = FormWindowState.Maximized;

this.Activate();
}

private void notifyIcon1_BalloonTipShown(object sender, EventArgs


e)
{

private void toolStripContainer1_TopToolStripPanel_Click(object


sender, EventArgs e)
{

private void Ide_FormClosing(object sender, FormClosingEventArgs


e)
{
DialogResult dialogo = MessageBox.Show(" Desea cerrar el
Analizador ?","Cerrar Compilador", MessageBoxButtons.OKCancel,
MessageBoxIcon.Question);
if (dialogo == DialogResult.OK) {
System.Windows.Forms.Application.Exit();
}
else {
e.Cancel = true;
}

private void acercaDeCompEdToolStripMenuItem_Click(object


sender, EventArgs e)
{

private void abrirToolStripMenuItem_Click(object sender, EventArgs


e)
{
abrirarchivo();
}

//-----------------------------METODOS DE ARCHIVOS
-----------------------------------------

public void exportaraexcel(DataGridView tabla)


{

Microsoft.Office.Interop.Excel.Application excel = new


Microsoft.Office.Interop.Excel.Application();

excel.Application.Workbooks.Add(true);

int ColumnIndex = 0;

foreach (DataGridViewColumn col in tabla.Columns)


{

ColumnIndex++;

excel.Cells[1, ColumnIndex] = col.Name;

int rowIndex = 0;

foreach (DataGridViewRow row in tabla.Rows)


{

rowIndex++;

ColumnIndex = 0;

foreach (DataGridViewColumn col in tabla.Columns)


{

ColumnIndex++;

excel.Cells[rowIndex + 1, ColumnIndex] =
row.Cells[col.Name].Value;
}
}
excel.Visible = true;
Worksheet worksheet = (Worksheet)excel.ActiveSheet;

worksheet.Activate();
}

public void abrirarchivo()


{
try{
OpenFileDialog ofd = new OpenFileDialog();
ofd.Title = "CompEd#
Archivo

Abrir
";

ofd.ShowDialog();
// ofd.Filter = "Archivos ed#(*.ed)|*.ed";
if (File.Exists(ofd.FileName))
{
using (Stream stream = ofd.OpenFile())
{
//MessageBox.Show("archivo encontrado: "+ofd.FileName);
leerarchivo(ofd.FileName);
nomarchivox = ofd.FileName;

txt_direccion.Text =ofd.FileName;
tabControl1.Visible = true;
}

}
}catch(Exception){

MessageBox.Show("El archivo no se abrio correctamente");

tabla_errorres.addliste(2);
}

public void leerarchivo(string nomarchivo)


{
StreamReader reader = new StreamReader(nomarchivo,
System.Text.Encoding.Default);
//string read = reader.ReadLine();
string texto;
// while (read != null)
//{
texto = reader.ReadToEnd();
// read = read + "\n";

reader.Close();

PagCodigo.Text = texto;
// read =reader.ReadLine();

//}

public bool revisasiarchivoexiste(string nomarchivo)


{

bool existe;

if (File.Exists(nomarchivo))
{
// el archivo existe
existe = true;
}
else
{
// el archivo no extiste
existe = false;
}
return existe;
}

public void guardaArchivo()


{
SaveFileDialog saveFile = new SaveFileDialog();
saveFile.Filter = "Archivos ed|*.ed";
if (saveFile.ShowDialog() == DialogResult.OK)
{

if (File.Exists(saveFile.FileName))
{
// el archivo existe
//------------------- para un log que agrega eventos ..................
//StreamWriter writer = File.AppendText(nomarchivo);
//writer.WriteLine("\n <</ ---Actualizacion del " +
DateTime.Now.ToString() + " />>");
//writer.Write(PagCodigo.Text);
//writer.Close();

//------------------ para sobrescribir el texto ...................


StreamWriter codigonuevo =
File.CreateText(saveFile.FileName);
codigonuevo.Write(PagCodigo.Text);
codigonuevo.Flush();
codigonuevo.Close();
nomarchivox = saveFile.FileName;
txt_direccion.Text = saveFile.FileName;

}
else
{
// el archivo no extiste

StreamWriter codigonuevo =
File.CreateText(saveFile.FileName);
codigonuevo.Write(PagCodigo.Text);

codigonuevo.Write("\n \n <</ Archivo creado el: " +


DateTime.Now.ToString() + " />> \n ");
codigonuevo.Flush();
codigonuevo.Close();
nomarchivox = saveFile.FileName;
txt_direccion.Text = saveFile.FileName;
}
}
}
public void guardaArchivo2(string nomarchivo)
{ try
{
if (nomarchivo == null)
{ guardaArchivo();

}
else
{
// el archivo nuevo
StreamWriter codigonuevo = File.CreateText(nomarchivo);
codigonuevo.Write(PagCodigo.Text);
codigonuevo.Flush();
codigonuevo.Close();
}
}
catch (Exception)

{
MessageBox.Show("error al guardar");
}
}
public void leer_archivo_al(string nomarchivo)
{

int contador_Ambitoi =0;


int contador_Ambitf = 0;
int ambito = 0;
try
{
StreamReader reader = new StreamReader(nomarchivo);
string[] Palabras_Separadas;
string read;
int numero_de_lineas = 0;
PagCodigo.Select(0, PagCodigo.SelectionStart);

while (reader != null)


{
numero_de_lineas = numero_de_lineas + 1;
read = reader.ReadLine();

if (reader.EndOfStream)
{

//MessageBox.Show("ultima linea");

break;
}
else
}
Palabras_Separadas = read.Split(' ');
foreach (var palabra in Palabras_Separadas)
{
#region Medicion del ambito

if (palabra == "{")
{
contador_Ambitoi = contador_Ambitoi + 1;
}
if (palabra == "}")
{
contador_Ambitf = contador_Ambitf + 1;
}
ambito = contador_Ambitoi;

#endregion
//----------------------------------------------------------------------if (tabla_simbolos.compararAL(palabra.ToString()) && palabra != null)//
se manda a comparar la palabra con la tabla de simbolos

{
//
,tam,ambit,

simb ,val, nunlin


id_,

tipo,

descrip

//uneSentencias();
tabla_de_simbolos objnuevo = new tabla_de_simbolos(palabra, "",
numero_de_lineas, -0, ambito,
tabla_simbolos.compararALRef(palabra.ToString()), "palabra nueva",
"palabra que coincide con la Tabla de simbolos", "");
tabla_simbolos.aadir_obj(objnuevo);

PagCodigo.SelectionStart = PagCodigo.Find(palabra);
PagCodigo.SelectionColor = Color.DodgerBlue;

}
else//de no estar en la tabla de simbolos se agrega a
un campo nuevo
{
if (Regex.IsMatch(palabra, @"[a-zA-Z]") && palabra !
= null)//sentencia que revisa los dos texbox
{
//
System.Windows.Forms.MessageBox.Show("esto es una palabra");
tabla_de_simbolos objnuevo = new
tabla_de_simbolos(palabra, "", numero_de_lineas, -0, ambito,
tabla_simbolos.contlineas() + 1, "palabra nueva", "palabra que no
coincide con la Tabla de simbolos,pero no se considera error","");
tabla_simbolos.aadir_obj(objnuevo);
}
else if (Regex.IsMatch(palabra,
@"\d{1}|\d{2}|\d{3}|\d{4}|\d{5}") && palabra != null)

{
//System.Windows.Forms.MessageBox.Show("esto
es un numero");
tabla_de_simbolos objnuevo = new
tabla_de_simbolos(palabra, palabra, numero_de_lineas, -0, ambito,
tabla_simbolos.contlineas() + 1, "numero nuevo", "numero","");
tabla_simbolos.aadir_obj(objnuevo);

PagCodigo.SelectionStart =
PagCodigo.Find(palabra);
PagCodigo.SelectionColor = Color.Aquamarine;

}
else
{
//
System.Windows.Forms.MessageBox.Show("Error en la expresion \n no
cumple con un formato correcto ");

}
}
}//fin del analisis lexico

}
Palabras_Separadas = null;
cantLineas = numero_de_lineas;
}

if (contador_Ambitf != contador_Ambitoi)
{
//MessageBox.Show("error de ambito");
tabla_errorres.addliste(8);

reader.Close();
}
catch (ArgumentNullException)
{

MessageBox.Show("El archivo no se abrio correctamente");

tabla_errorres.addliste(2);
}
catch (Exception)
{
MessageBox.Show("error");
}

public string[] uneSentencias (){


string sentencia = null;
string[] sentencias = new string[cantLineas];
int bandera = 0;
string tipov = "";

for (int i = 1; i < cantLineas; i++) //une los token de cada linea
{
foreach (var token in tabla_simbolos.llamatabla())
{
if (token.NumLinea == i && token != null)
{
if (bandera == 0 && Regex.IsMatch(token.Simbolo,
@"(<#int|<#integer|<#double|<#bool|<#string|<#real|<#boolean)
$"))
{
token.TipoVar = token.Simbolo;
tipov = token.Simbolo;
}

if (bandera != 0)
{
sentencia = sentencia + " " + token.simbolo.ToString();
token.TipoVar = tipov;
}
else

{
sentencia = sentencia + token.simbolo.ToString();
bandera = 1;
}

}
}
sentencias[i] = sentencia;
sentencia = null;
bandera = 0;
tipov = "";
}

return sentencias;
}
#region analizador sintactico
public void AnlzdrSntctc(string[] sentencias)
{

for (int i = 1; i < sentencias.Length; i++)


{
//MessageBox.Show(sentencias[i]);
#region Expresiones regulares
if (sentencias[i] != null)
{

if (Regex.IsMatch(sentencias[i], @"^<#int|<#integer\s+[az](1,15)(\s+:\s+\d(0,32000))*;$"))
{

System.Windows.Forms.MessageBox.Show("esto es una
sentencia int");
#region parte semantica
string[] separanum;
separanum = sentencias[i].Split(' ');
try{
int num ;
num = int.Parse(separanum[3]);

MessageBox.Show("si es un numero entero");

}catch(FormatException e){

MessageBox.Show("no es un numero entero");


tabla_errorres.addliste(0,i);

}catch(IndexOutOfRangeException e){

tabla_errorres.addliste(10, i);
MessageBox.Show("error de escritura");

}
#endregion

}
else if (Regex.IsMatch(sentencias[i], @"^<#double|
<#real\s+[a-z](1,15)(\s+:\s+\d(0,32000))*;$"))
{
System.Windows.Forms.MessageBox.Show("esto es una
sentencia double");
#region parte semantica
string[] separanum;
separanum = sentencias[i].Split(' ');
try
{
double num;
num = double.Parse(separanum[3]);

MessageBox.Show("si es un numero double");

}
catch (FormatException e)
{
tabla_errorres.addliste(0,i);
MessageBox.Show("no es un numero double");

}catch(IndexOutOfRangeException e){

tabla_errorres.addliste(10, i);

MessageBox.Show("error de escritura");

#endregion

}
else if (Regex.IsMatch(sentencias[i], @"^<#string|
<#texto\s+[a-z](1,15)(\s+:\s+[a-z](1,15)')*;$"))
{
System.Windows.Forms.MessageBox.Show("esto es una
sentencia string");

}
else if (Regex.IsMatch(sentencias[i], @"^<#bool|
<#boolean\s+[a-z](1,15)(\s+:\s+(true|false))*;$"))
{
System.Windows.Forms.MessageBox.Show("esto es una
sentencia bool");

#region parte semantica


string[] separavar;
separavar = sentencias[i].Split(' ');
try
{
bool var;
var = bool.Parse(separavar[3]);

MessageBox.Show("si es una variable bool");

}
catch (FormatException e)
{

MessageBox.Show("no es una variable bool");


tabla_errorres.addliste(0, i);
}
#endregion

}
else if (Regex.IsMatch(sentencias[i], @"<<*.*>>$"))
{
MessageBox.Show("Esto es un comentario");
}
else if (Regex.IsMatch(sentencias[i], @"[a-z]\s+:\s[a-z]|
(\w)*\s\+\s(\w)*|\d(0,32000)*\s;$"))
{
MessageBox.Show("esto es una sentecia de asignacion");

#region parte semantica


string tpv1 = "";
string tpv2 = "";
string tpv3 = "";

string[] separavar;
separavar = sentencias[i].Split(' ');

if (Regex.IsMatch(sentencias[i], @"[a-z]\s+:\s(\w)*\s\
+\s(\w)*\s;$"))//-- asignacion del tipo monto : num1 + num2 ;
{

foreach (var token in tabla_simbolos.llamatabla())


{
if (token.Simbolo == separavar [0])
{
tpv1 = token.TipoVar;
}
if (token.Simbolo == separavar[2])
{
tpv2 = token.TipoVar;
}
if (token.Simbolo == separavar[4])
{
tpv3 = token.TipoVar;
}

}//-- fin del foreach


if (tpv1 == tpv2 && tpv2 == tpv3 && tpv1 != "")
{

MessageBox.Show("el tipo de las variables son el


mismo");
}
}
if (Regex.IsMatch(sentencias[i], @"[az]\s+:\s(\w)*\s\-\s(\w)*\s;$"))//-- asignacion del tipo monto : num1 - num2
;
{

foreach (var token in tabla_simbolos.llamatabla())


{
if (token.Simbolo == separavar[0])
{
tpv1 = token.TipoVar;
}
if (token.Simbolo == separavar[2])
{
tpv2 = token.TipoVar;
}
if (token.Simbolo == separavar[4])
{
tpv3 = token.TipoVar;
}

}//-- fin del foreach


if (tpv1 == tpv2 && tpv2 == tpv3 && tpv1 != "")
{

MessageBox.Show("el tipo de las variables son el


mismo");
}
}
if (Regex.IsMatch(sentencias[i], @"[az]\s+:\s(\w)*\s\/\s(\w)*\s;$"))//-- asignacion del tipo monto : num1 / num2
;
{

foreach (var token in tabla_simbolos.llamatabla())


{
if (token.Simbolo == separavar[0])
{
tpv1 = token.TipoVar;
}
if (token.Simbolo == separavar[2])
{
tpv2 = token.TipoVar;
}
if (token.Simbolo == separavar[4])
{
tpv3 = token.TipoVar;
}

}//-- fin del foreach


if (tpv1 == tpv2 && tpv2 == tpv3 && tpv1 != "")
{

MessageBox.Show("el tipo de las variables son el


mismo");
}
}
if (Regex.IsMatch(sentencias[i], @"[az]\s+:\s(\w)*\s\*\s(\w)*\s;$"))//-- asignacion del tipo monto : num1 *
num2 ;
{

foreach (var token in tabla_simbolos.llamatabla())


{
if (token.Simbolo == separavar[0])
{
tpv1 = token.TipoVar;
}
if (token.Simbolo == separavar[2])
{
tpv2 = token.TipoVar;
}
if (token.Simbolo == separavar[4])
{
tpv3 = token.TipoVar;
}

}//-- fin del foreach


if (tpv1 == tpv2 && tpv2 == tpv3 && tpv1 != "")
{

MessageBox.Show("el tipo de las variables son el


mismo");
}
}

#endregion

}
else if (Regex.IsMatch(sentencias[i], @"^{$"))
{
MessageBox.Show("inicio de ambito");
}
else if (Regex.IsMatch(sentencias[i], @"^}$"))
{
MessageBox.Show("fin de ambito");
}
else if (Regex.IsMatch(sentencias[i], @"<<si_\s\(\s+\w+\s(<|
>|<:|>:|::|!:)\s\w+\s\)\s\{$"))//-{
MessageBox.Show("comienzo de if");
}
else if (Regex.IsMatch(sentencias[i], @"<<ysi_\s\
(\s+\w+\s(<|>|<:|>:|::|!:)\s\w+\s\)\s\{$"))//-{
MessageBox.Show("comienzo de else if");

}
else if (Regex.IsMatch(sentencias[i], @"<<sino\s*\{$"))//-{
MessageBox.Show("comienzo de else");
}
else if (Regex.IsMatch(sentencias[i], @"#ncasd\s\(\s\w+\s(<|
>|<:|>:|::|!:)\s\w+\s\)\s\{$"))//-{
MessageBox.Show("comienzo del switch");
}
else if (Regex.IsMatch(sentencias[i], @"casd\s\
(\s(\w+|\d+)\s\)\s{$"))//-{
MessageBox.Show("comienzo de case");
}
else if (Regex.IsMatch(sentencias[i], @"fcasd\s;$"))//-{
MessageBox.Show("break del case");
}
else if (Regex.IsMatch(sentencias[i], @"#mintrs\s\
(\s\w+\s(<|>|<:|>:|::|!:)\s\w+\s\)\s{$"))
{
MessageBox.Show("inicio de un while");
}

else if (Regex.IsMatch(sentencias[i], @"#mostrar\s\


(\s(\w*)|'\w*'\)\s;$"))

{
MessageBox.Show("mostrar por pantalla \n" +
sentencias[i]);

}
//else if (Regex.IsMatch(sentencias[i],@""))
//{
//MessageBox.Show("");
//}
//else if (Regex.IsMatch(sentencias[i],@""))
//{
//MessageBox.Show("");
//}
//else if (Regex.IsMatch(sentencias[i],@""))
//{
//MessageBox.Show("");
//}
//else if (Regex.IsMatch(sentencias[i],@""))
//{
//MessageBox.Show("");
//}
else
{
if (sentencias[i] != null)
{
tabla_errorres.addliste(9, i);

//MessageBox.Show("Expresion invalida");
}
}
}

#endregion

//System.Windows.Forms.MessageBox.Show("" +
sentencias[i]);
}

}
#endregion

private void guardarToolStripMenuItem_Click(object sender,


EventArgs e)
{
guardaArchivo();
}

private void toolStripButton3_Click(object sender, EventArgs e)


{
guardaArchivo2(nomarchivox);

private void guardarToolStripMenuItem1_Click(object sender,


EventArgs e)
{
guardaArchivo2(nomarchivox);

private void nuevoToolStripMenuItem_Click(object sender,


EventArgs e)
{
tabControl1.Visible = true;

private void toolStripButton8_Click(object sender, EventArgs e)


{
dataGridView1.DataSource = null;
dataGridView2.DataSource = null;
dataGridView1.DataSource = tabla_simbolos.llamatabla();

dataGridView2.DataSource = tabla_errorres.llamatablaE();

private void analizadorLexicoToolStripMenuItem_Click(object


sender, EventArgs e)
{
leer_archivo_al(nomarchivox);
}

private void toolStripButton9_Click(object sender, EventArgs e)


{
tabControl1.Visible = true;

private void cerrarProyectoToolStripMenuItem_Click(object sender,


EventArgs e)
{
tabControl1.Visible = false ;

private void toolStripButton6_Click(object sender, EventArgs e)


{
abrirarchivo();
}

private void maximizarVentanaToolStripMenuItem_Click(object


sender, EventArgs e)
{
this.WindowState = FormWindowState.Maximized;
}

private void minimizarVentanaToolStripMenuItem_Click(object


sender, EventArgs e)
{
this.WindowState = FormWindowState.Normal;
}

private void minimizarVentanaToolStripMenuItem1_Click(object


sender, EventArgs e)
{
this.WindowState = FormWindowState.Minimized;
}

private void opcionesToolStripMenuItem_Click(object sender,


EventArgs e)
{

private void colorDeLaFuenteToolStripMenuItem_Click(object


sender, EventArgs e)
{

var cl = colorDialog1.ShowDialog();
if (cl == System.Windows.Forms.DialogResult.OK)
{
//PagCodigo.SelectionColor = colorDialog1.Color; <..... esto
para una parte del texto
PagCodigo.ForeColor = colorDialog1.Color;
}

private void colorDeConsolaToolStripMenuItem_Click(object sender,


EventArgs e)
{
var cl = colorDialog1.ShowDialog();
if (cl == System.Windows.Forms.DialogResult.OK)
{
//PagCodigo.SelectionColor = colorDialog1.Color; <..... esto
para una parte del texto
PagCodigo.BackColor = colorDialog1.Color;
}

private void formatoToolStripMenuItem_Click(object sender,


EventArgs e)
{

var fm = fontDialog1.ShowDialog();
if (fm == DialogResult.OK)
{
//PagCodigo.SelectionColor = colorDialog1.Color; <..... esto
para una parte del texto
PagCodigo.Font = fontDialog1.Font;
}

private void toolStripButton2_Click(object sender, EventArgs e)


{
if (Cb_resultados.Text == "ver log de errores")
{
exportaraexcel(dataGridView2);
}
else if (Cb_resultados.Text == "ver log de simbolos")
{
exportaraexcel(dataGridView1);
}

private void toolStripButton5_Click(object sender, EventArgs e)


{
guardaArchivo2(nomarchivox);
tabla_simbolos.reinicialista();
tabla_errorres.reinicialista();
tabla_errorres.inicialestaE();
tabla_simbolos.inicialista();
leer_archivo_al(nomarchivox);
string[] sent = uneSentencias();
tabla_simbolos.compararALsemantic();

if (tabla_simbolos.revisar_duplicados())
{
tabla_errorres.addliste(11);
}
AnlzdrSntctc(sent);
dataGridView1.DataSource = null;
dataGridView2.DataSource = null;
dataGridView1.DataSource = tabla_simbolos.llamatabla();
dataGridView2.DataSource = tabla_errorres.llamatablaE();
System.Media.SystemSounds.Asterisk.Play();

ACTIVIDAD 8. NUESTRO PROYECTO A DESARROLLAR SER UN COMPILADOR


QUE INCLUYA EL ANALIZADOR LEXICO, SINTACTICO Y SEMANTICO.
PROGRAMA: ANALIZADOR SEMANTICO ELABORADO EN MICROSFT VISUAL C# 2013

Desarrollar e implementar un analizador que se encarga de chequear el texto de


entrada en base a una gramtica dada. Y en caso de que el programa de entrada
sea vlido, suministra el rbol sintctico que lo reconoce.
En teora, se supone que la salida del analizador semntico ser alguna
representacin del rbol sintctico que reconoce la secuencia de tokens
suministrada por el analizador lxico. En la prctica, el analizador semntico
tambin realizara:

Acceder a la tabla de smbolos (para hacer parte del trabajo del analizador
semntico).
Chequeo de tipos (del analizador semntico).
Generar cdigo intermedio.
Generar errores cuando se producen.

En definitiva, realiza casi todas las operaciones de la compilacin. Este mtodo de


trabajo da lugar a los mtodos de compilacin dirigidos por sintaxis.

Metodologia a utilizar???

CONCLUSIN
Aprend que las herramientas que muestran tipos de anlisis de programas fuente,
son muy tiles al momento de crear un programa al codificar un algoritmo, ya que
estas herramientas nos ayudan formateando el texto, corrigiendo errores, dando
tips; para que nosotros como programadores seamos ms eficientes al momento
de
crear
alguna
aplicacin.
Por otro lado, comprend que un compilador, requiere de una sintaxis y lenguajes
especficos, ya que, al igual que el lenguaje humano, si no lo escribimos

correctamente el compilador no har lo que deseamos. Y que en la compilacin


hay dos partes: Anlisis y Sntesis. La parte del anlisis divide al programa fuente
en sus elementos componentes y crea una representacin intermedio.
El analizador semntico tiene dos objetivos:
Hacer comprobaciones que no se hagan durante el anlisis lxico o sintctico.
Crear una representacin adecuada para fases posteriores. Implementaremos el
anlisis semntico en dos partes:
Mediante esquemas de traduccin dirigidos por la sintaxis.
Recorriendo el AST. Un esquema de traduccin dirigido por la sintaxis aade a
las gramticas: Acciones intercaladas en las partes derechas de las reglas.
Atributos asociados a los no terminales. Dos tipos de atributos: heredados y
sintetizados. Las acciones deben garantizar que se evalan correctamente los
atributos. Se pueden implementar los esquemas de traduccin sobre los
analizadores sintcticos interpretando los atributos como parmetros y aadiendo
el cdigo de las acciones al cdigo del analizador. El clculo de algunos atributos y
algunas comprobaciones semnticas son ms fciles sobre el AST. La tabla de
smbolos se puede implementar eficientemente mediante una tabla hash.
Las comprobaciones de tipos se complican si se introducen nombres.
Dos criterios:
Equivalencia de nombre.
Equivalencia estructural.

Bibliografa
(29 de 10 de 2014). Obtenido de
http://es.wikipedia.org/wiki/Visual_Basic_alfabeto a partir de un lenguaje

(29 de 10 de 2014). Obtenido de


http://www.paginasprodigy.com/edserna/cursos/compilador/notas/Notas1
.pdf
(29 de 10 de 2014). Obtenido de
http://es.slideshare.net/GonzaloSantiago/teoria-de-lenguajes-gramaticasy-automatas-para-informaticos
A.V.Aho, J. (1994). Foundations of Computer Science. En J. A.V.Aho, Sciense
Press (pgs. 156-162). Nueva York.
J.Hartmanis, R. y. (1963). Regulatiry-preserving modificacations of regular
expressions. inglaterra.
McCarthy, C. S. (1956). ,Gedanken experiments on sequential machines. USA.
S.C.Kleene. (1956). estudio de automatas. estados unidos.
UNAM. (03 de noviembre de 2014). Obtenido de http://bibliotecas.unam.mx/
UNAM. (03 de noviembre de 2014). Obtenido de
http://bibliotecas.unam.mx/index.php/bibliotecasunam_libro el estudio
de lenguajes y automatas

Das könnte Ihnen auch gefallen