Una volta
acquisite le nozioni contenute in Structured Operational Semantics of a fragment of
the language Scheme di Honsell, Pravato, Ronchi Della Rocca vediamo come applicarle
per la risoluzione di un esercizio tipico.
Descrivere gli ambienti della seguente sessione SCHEME :
(lambda (x) (+ (let ((x 1)
(fun
(lambda (y) (+ x 1))))
(fun
x)) (+ x x)) ))
(define t 44)
(define x 8)
(let ((x (+ x 2))
(gg (lambda (y) t))
(t 66)
(fun 21))
(
(lambda (x) (+ (gg 1) fun)) ((K fun) x) ))
Trattiamo la descrizione distinguendo i vari
passi.
Sia P_Atop il puntatore al top level environment.
- Leggiamo
la definizione di una funzione (define (K x)
), perciò si crea lassociazione
nome funzione à <1° argomento
chiusura, 2° argomento chiusura >, in cui il 1° argomento della chiusura è la
definizione della funzione, mentre il secondo indica il puntatore allambiente in cui
abbiamo dichiarato la funzione : stiamo applicando la regola (dec 2).

- Leggiamo (define t 44) quindi aggiungiamo allambiente corrente la nuova
associazione (dec 1):

- Leggiamo
(define x 8) quindi aggiungiamo allambiente corrente la nuova associazione (dec 1):

Valutiamo (let ((x (+ x 2))
(gg (lambda (y) t))
(t 66)
(fun 21))
(
(lambda (x) (+ (gg 1) fun)) ((K fun) x) )).
Nellambiente corrente calcoliamo
il valore dei secondi argomenti delle coppie del let ed estendiamo lambiente con un
nuovo frame che contiene le nuove associazioni.

- Dobbiamo
valutare (lambda
(x) (+ (gg 1) fun)) il cui valore è la chiusura
< lambda (x) (+ (gg 1) fun)) , p2 > (1) (lambda).
La valutazione dellargomento ((K fun) x )
implica quella di (K fun)
e cioè K
nel frame puntato da p2 .
Il valore di K si trova in P_Atop, cerchiamo quello di fun a partire da p2
verso P_Atop e lo troviamo in p2 (appl 1).
Estendiamo lambiente con un nuovo frame contenente lassociazione parametri
formali / parametri attuali di K: x à 21 e vi
valutiamo
(lambda (x)(+
(let ((x 1) (fun (lambda (y) (+ x 1)))) (fun x)) (+ x x)) )).

- Il valore di (lambda (x) (+ (let ((x 1)
(fun (lambda (y) (+ x 1)))) (fun x))
(+ x x)) )) è la chiusura < lambda
(x) (+ (let ((x 1)(fun (lambda (y) (+ x 1))))(fun x))
(+ x x)) ), p3>. Recuperiamo
il valore da assegnare a x relativo a (lambda
) e sarà quello contenuto nel frame
puntato da p2 per questione di scoping, e procediamo con la solita estensione
con un nuovo frame:

- Si tratta di unaddizione, quindi applichiamo la regola (appl 2): un argomento è
il let, perciò

- Valutiamo in
p5 fun x recuperando tramite la regola (var 1) le associazioni x à 1 e fun à < lambda
(y) (+ x 1), p4 >; quindi valutiamo il corpo di fun in p4 calcolando fun x = 11. I frame puntati da p5
e p5bis non servono più, quindi li eliminiamo. Per laddizione interna (+
x 1) abbiamo utilizzato (appl 2) la quale non ha modificato lambiente.

- Adesso
calcoliamo laltro termine delladdizione: (+ x x) nel frame puntato da p4: a x
è associato il valore 10 quindi (+ x x) vale 20. Perciò il valore di (+ (let ((x
1) (fun (lambda (y) (+ x 1)))) (fun x)) (+ x x)) )) è 31 e
cancelliamo p3 e p4 e i frame ad essi relativi. Abbiamo così terminato al valutazione di
((K fun) x).

- Prima abbiamo calcolato il valore di (lambda (x) (+ (gg 1)
fun)) dato dalla chiusura (1) del
punto 5. Possiamo quindi valutare lapplicazione: estendiamo lambiente con un
nuovo frame.

- Calcoliamo (+
(gg 1) fun)) in p6. Cerchiamo gg che si trova nel frame indicato da p2
ed appendiamo a P_Atop il frame contenente lassociazione y à 1 in cui
si valuterà il corpo dellapplicazione gg.

- Il valore di t è 44, poi valutiamo fun che ha valore 21 ed eseguiamo laddizione.
Il valore di (+ (gg 1) fun)) è
così 65. I puntatori p2, p6 e p7 non sono più necessari
e possiamo eliminarli.