Guía Corta: Alcance y Asociaciones 1. Preliminares: Nombres

Anuncio
Universidad Simón Bolívar
Departamento de Computación y Tecnología de la Información
CI3641 Lenguajes de Programación I
Guía Corta: Alcance y Asociaciones
Esta guía presenta algunos conceptos básicos y ejemplos para entender las diferencias entre
alcance estático y dinámico, así como entre asociación supercial y profunda.
Nota: Es importante recordar que esta guía es un complemento, cuyo objetivo es ayudar al
entendimiento de estos conceptos y su aplicación en la práctica. No debe considerarse un reemplazo
para la bibliografía ocial del curso.
1.
Preliminares: Nombres y Asociaciones
Recordemos que un
nombre,
en el contexto de lenguajes de programación, es cualquier ca-
dena de caracteres cuyo objetivo es representar algo más. Por ejemplo: identicadores, palabras
claves e incluso operadores. Una
asociación
es el lazo que relaciona dichos nombres con aquello
que representa. Estas asociaciones pueden ser: identicadores a valores (incluyendo sus tipos,
direcciones de memoria, etc.), palabras claves y operadores a sus semánticas (comportamiento
esperado), tipos a sus representaciones concretas de bajo nivel, etc.
El
momento de asociación
es aquel en el que una determinada asociación es denida. Esto
es, el momento en que un nombre es efectivamente asociado con su signicado. Los momentos de
asociación se pueden agrupar por etapas distintivas, presentadas a continuación:
Asociación temprana/estática
Asociación tardía/dinámica
Denición del lenguaje
Carga
Implementación del traductor o intérprete
Ejecución
Programación
Compilación (incluyendo preprocesamientos)
Enlace
Cuadro 1: Clasicación de momentos de asociación.
Es importante notar que la separación aparente entre momentos de asociación es difusa, más
aún su clasicación como
temprana
o
tardía. Algunos lenguajes permiten hacer compilación JIT
(just in time), que permite compilar código solamente cuando es necesario. Esta compilación JIT
hace que muchas asociaciones que se hacen a tiempo de compilación se hagan de forma dinámica.
Así mismo, algunos lenguajes implementan optimizaciones de código donde expresiones constantes
son evaluadas antes de comenzar la ejecución del programa. Esta optimización hace que algunas
asociaciones que corresponden a tiempo de ejecución se hagan de forma estática.
El
tiempo de vida
de una asociación es un concepto dinámico, el cual dene los períodos de
tiempo en los que una determinada asociación para un nombre está activa. Por ejemplo, el tiempo
de vida de una constante global de compilación es la de todo el programa y el tiempo de vida de
una constante global de elaboración es desde el momento en que le es asignado un valor, hasta
la terminación del programa.
1
2.
Alcance
El
alcance
de una asociación es la porción léxica (en el código) de un programa, donde la
asociación en cuestión está
activa. En particular, una asociación cuyo alcance es importante es la
de identicadores con variables (o constantes). Una instrucción de la forma int
x = 3;
declara
una variable, de tipo entero y con el valor 3. Tanto el tipo como el valor están asociados ahora
al nombre
x.
Sin embargo, es mucho más util considerar que al identicador se ha asociado una
variable, que a su vez tiene asociado un tipo y un valor. De esta manera, posteriores asignaciones
a
x
no alteran la asociación, sino solamente la variable que está asociada.
Algunos lenguajes de programación permiten que variables locales
escondan
asociaciones,
segmentando el alcance de las mismas. La gura 1 muestra un ejemplo de cómo la primera
asociación de
x
(verde claro) puede ser escondida por la segunda (verde oscuro).
Figura 1: Ejemplo de segmentación de alcance.
El programa mostrado imprimiría:
3 4 3.
Pregunta:
¾Si la declaración interior se reemplazara por sólo una asignación, qué imprimiría entonces?
Consideremos ahora el programa presentado en la gura 2 y para el mismo intentemos predecir
lo que imprime.
Figura 2: Programa de ejemplo.
La respuesta es... ½Depende!
Lo más intuitivo sería suponer que imprime 3, ya que es el valor de la variable global
el procedimiento
p2
x
y
no introduce nuevas asociaciones locales. A este comportamiento, donde el
alcance viene dado por la disposición del código, se le conoce como
alcance estático. Sin embargo
se puede plantear que la asociación activa sea aquella que haya sido más recientemente creada y no
2
destruida. En ese caso, la asociación activa sería la de la
se le conoce como
alcance dinámico.
Alcance estático:
x declarada en p1. A este comportamiento
Se basa en la disposición del código.
El programa de la gura 2 imprimiría 3.
Alcance dinámico:
Se basa en la ejecución del código.
El programa de la gura 2 imprimiría 4.
Pregunta:
¾Qué ventajas y desventajas puede traer a un programador contar con un lenguaje de alcance
estático o dinámico?
Si se permite la declaración de subrutinas anidadas y pasaje de subrutinas como parámetros,
los ejemplos puede ser mucho más oscuros. Consideremos ahora el programa en la gura 3:
Figura 3: Programa de ejemplo con subrutinas anidadas.
¾Que imprime este programa?
3.
Clausuras y asociaciones
Aún no contamos con las herramientas necesarias para responder que imprime el programa de
la gura 3, para ello debemos introducir el concepto de
clausura. Una clausura no es más que el
contexto nolocal que necesita un procedimiento para poder ejecutarse. En el caso del programa
p2 utiliza una variable y, que no es parte de sus variables
p2! Una clausura para este procedimiento consistiría en un
anterior, vemos que el procedimiento
locales ni parámetros. ½Es externa a
apuntador a esta variable
La clausura para
p2
y,
la cual será usada al momento de invocarse.
podría hacerse en uno de dos momentos:
El momento en que la subrutina es pasada como argumento por primera vez. A esta estrategia se le conoce como
asociación profunda.
Bajo esta estrategia, el programa de la gura 3 imprimiría 4. ¾Por qué no 8?
3
El momento en que la subrutina es nalmente invocada. A esta estrategia se le conoce como
asociación supercial.
Bajo esta estrategia, el programa de la gura 3 imprimiría 2.
En situaciones en el que el tipo de asociación (supercial o profunda) es relevante, el alcance
estático puede ser dependiente de la ejecución. La misma gura 3 presenta un ejemplo. Aún con
alcance estático, el tipo de asociación determinó la instancia de la variable
autores preeren llamar a este tipo de alcance
léxico, en vez de estático.
y.
Por esto, muchos
Pregunta:
¾Un mismo programa puede arrojar cuatro resultados diferentes, al considerar las combinaciones
de alcance estático/dinámico y asociación profunda/supercial? De ser así, escriba tal programa.
4.
El camino del bien
A continuación les propongo lo que considero
el camino del bien
para resolver problemas que
traten de alcance y asociaciones:
Dibujar una pila, donde inicialmente solo están empiladas las variables globales.
Cada vez que se haga una llamada a un procedimiento, empilar sus argumentos.
•
En el caso en que la asociación sea profunda, para cada procedimiento pasado como
argumento se construye una clausura (tabla de símbolos externa) donde cada casilla
tiene el nombre de la variable y una echa hacia la casilla en la pila que contiene su
información.
•
En el caso en que la asociación sea supercial y el procedimiento invocado sea una
variable, se construye una clausura para el mismo.
Al pasar a dicho procedimiento, hacer explícito el cambio en la pila dibujada e incluir una
echa al último bloque presente en la pila, que sea inmediatamente externo a él, en término
léxicos.
Cada nueva declaración de variable la empila junto con su valor. Las declaraciones de
procedimientos internos son ignoradas.
Al buscar valores de variables se hace buscando el más reciente en la pila si se está usando
alcance dinámico, o el más reciente siguiendo la cadena de apuntadores a bloques léxicos,
construida anteriormente si se está usando alcance estático.
Estas instrucciones serán practicadas en clase (o en un video, en su defecto). Sin embargo, les
adelanto la gura 4 como un primer ejemplo de esto.
4
Figura 4: Ejemplo del camino del bien.
El programa utilizado fue sacado del 1er examen de EneroMarzo, 2012. La corrida corresponde a alcance estático y asociación profunda. La pila está construida hasta el momento en que
se ejecuta nalmente el procedimiento
5.
Q.
Ejericios sugeridos
Casi todos los primeros exámenes de la materia, como se ha dado durante los últimos años por
el prof. Ernesto HernandezNovich y mi persona, tienen una o más preguntas sobre ejecución de
programas con diferentes tipos de alcances y asociaciones. Les recomiendo buscen esos parciales
e intenten resolverlos. Pueden escribirme si tienen cualquier duda al respecto.
Ricardo Monascal / Febrero 2014
5
Descargar