UN TRADUCTOR PARA EXPRESIONES SIMPLES

Sintaxis abstracta y concreta: un punto de partida útil para considerar la traducción de una cadena de entrada es un árbol de sintaxis abstracta, donde cada nodo representa un operador, y los hijos de ese nodo, los operandos. Por contraste, un árbol de análisis sintáctico se denomina árbol de sintaxis concreta, y la gramática subyacente, sintaxis concreta del lenguaje. Los arboles de sintaxis abstracta, o simplemente arboles sintácticos difieren de los arboles de análisis sintáctico en que las distinciones superficiales de forma, sin importancia en la traducción, no aparecen en los arboles sintácticos.


Ejemplo:
El árbol sintáctico para 9-5+2 se muestra a continuación, dado que + y – tiene el mismo nivel de precedencia, y los operadores con igual nivel de precedencia, se evalúan de izquierda a derecha, el árbol presenta 9-5 agrupado como una buexpresion.




ejemplo propuesto: 8+3-5-2

Si no se ha definido el orden de evaluación de los operandos la siguiente optimización es válida
B=2*A+(A=c*d);
Pasar a
A=c*d;
B=A*3;
Adaptación del esquema de traducción: la técnica para la eliminación de la recursividad por la izquierda, se puede aplicar también a producciones que contengan acciones semánticas.

Cuando las acciones semánticas se intercalan en las producciones, se trasladan junto con la transformación. Aquí se hace A= expr, α=+ termino {print (‘+’)}, ϐ=- termino {print(‘-‘)} y y=termino,  esta traducción traduce esta transformación:
Expr -> termino resto
Resto -> termino {print(‘+)} resto|-termino{print(‘-‘)} resto| €
Termino ->0 {print(‘0’)}
Termino ->1 {print(‘1’)}
……
Termino ->9 {print(‘9’)}


Procedimiento para los no terminales: la función parea, es la contraparte en C del código ejemplo para aparear un componente léxico con el símbolo de preanalisis y avanzar por la entrada. Puesto que cada componente léxico es un solo carácter en este lenguaje, parea puede hacerse comparando y leyendo caracteres.



Las funciones para los no terminales imitan a los lados derechos de las producciones.
Por ejemplo, la producción expr -> termino resto se aplica para las llamadas a termino() y resto () en la función expr().


Simplificación del traductor: Ciertas llamadas recursivas de pueden remplazar por iteraciones. Cuando la ultima proposición ejecutada en el cuerpo de un procedimiento es una llamada recursiva al mismo procedimiento, se dice que la llamada es recursiva por el final. Por ejemplo las llamadas de resto() al final de la cuarta y séptima línea de la función resto () son recursivas por el final, por que el control fluye hacia el final del cuerpo de la función después de cada una de esas llamadas.

Se puede imprimir mayor velocidad a un programa remlazando la recursión por el final con una construcción de iteración. Para un procedimiento sin parámetros, una llamada recursiva por el final simplemente se puede remplazar por un salto al inicio del procedimiento.

El código de resto se puede rescribir como: 
Mientras el símbolo de pre análisis sea un signo mas o menos, el procedimiento resto parea el signo, llama a termino para que paree un digito, y repite el proceso.

0 comentarios:

Publicar un comentario