







Study with the several resources on Docsity
Earn points by helping other students or get them with a premium plan
Prepare for your exams
Study with the several resources on Docsity
Earn points to download
Earn points by helping other students or get them with a premium plan
Material Type: Exam; Class: Progrmg Languages & Compilers; Subject: Computer Science; University: University of Illinois - Urbana-Champaign; Term: Summer 2008;
Typology: Exams
1 / 13
This page cannot be seen from the preview
Don't miss anything!








11:30am–12:45pm, Monday, July 7, 2008
The total time for this exam is 75 minutes.
Print your name and netid below. Also write your name at the bottom of each subsequent page.
Name:
Netid:
Question Total points Score 1 10 2 15 3 15 4 8 5 12 6 20 7 20 SUBTOTAL 100 Extra Credit 12 TOTAL 112
(a) In the following, state TRUE or FALSE for each part separately; each part is 1 point (write your answers to the left): A typical dynamically-typed language: i. assigns types to all expressions at compile time FALSE ii. allows variables to hold values of different types at runtime TRUE iii. always detects all potential type errors in a program FALSE iv. checks that correct types are used in an expression when that expression is executed TRUE
(b) In the following, state TRUE or FALSE for each part separately; each part is 1 point (write your answers to the left): Lexing and parsing: i. any language construct that can be defined with a regular expression can also be defined with a context-free grammar TRUE ii. any language construct that can be defined with a context-free grammar can also be defined with a regular expression FALSE iii. an LL(1) parser can be created for any context-free grammar FALSE iv. LR parsing techniques are strictly more powerful than LL parsing techniques TRUE
(c) (2 points) What value is produced by the following program? let x = 5 and y = 10 in let y = x + y in let f x = x + y in let x = y + x in f x 35
You are allowed to use all functions in List, such as List.rev, List.fold left, etc – you do not have to write them yourself.
Given the following OCaml datatype: type list_tree = Empty | Node of list_tree * list_tree | Leaf of int list;; (a) (5 points) Write a recursive function fold list tree: val fold_list_tree : (’a -> ’a -> ’a) -> (int list -> ’a) -> ’a -> list_tree -> ’a =
(b) (5 points) Write a function prod list tree, using fold list tree, that will calcu- late the product of all the integers stored in the integer lists in the Leaf nodes of the list tree. 1 # let prod_list_tree lt = 2 fold_list_tree (fun x y -> x * y) (fun il -> List.fold_left ( * ) 1 il) 1 lt 3 val prod_list_tree : list_tree -> int =
(c) (5 points) Write a function flip list tree, using fold list tree, that will switch the left and right trees in any Node and reverse the lists stored in any Leaf. 1 # let flip_list_tree lt = 2 fold_list_tree (fun x y -> Node (y, x)) (fun il -> Leaf (List.rev il)) Empty lt;; 3 val flip_list_tree : list_tree -> list_tree =
(a) (4 points) Over the alphabet {a, b, c}, give a regular expression generating exactly those strings over {a, b, c} such that no b occurs after the final c. Remember, this does not mean the string needs to contain a c!
(a + b)∗^ + ((a + b + c)∗ca∗)
(b) (4 points) Over the alphabet {a, b, c}, give a regular expression generating exactly those strings over {a, b, c} where any a in the string occurs before any b but after at least one c (i.e. if there is an a in the string, there is at least one c before it; a mix of a and c characters can then occur, followed by a mix of b and c characters; if there is no a, c is allowed but not required.).
(c(c + a)∗(c + b)∗) + (b + c)∗
E → E + T T → T ∗ F F → id E → E − T T → T /F F → num E → T T → F F → (E)
(a) (5 points) Show a leftmost derivation for the following term: x ∗ y + (5 − 3)
E ⇒ E + T ⇒ T + T ⇒ T ∗ F + T ⇒ F ∗ F + T ⇒ x ∗ F + T ⇒ x ∗ y + T ⇒ x ∗ y + F ⇒ x ∗ y + (E) ⇒ x ∗ y + (E − T ) ⇒ x ∗ y + (T − T ) ⇒ x ∗ y + (F − T ) ⇒ x ∗ y + (5 − T ) ⇒ x ∗ y + (5 − F ) ⇒ x ∗ y + (5 − 3)
(b) (5 points) Show a rightmost derivation for the same term:
T ∗ y + (5 − 3) ⇒ F ∗ y + (5 − 3) ⇒ x ∗ y + (5 − 3)
E → E + T T → T ∗ F F → id E → E − T T → T /F F → num E → T T → F F → (E)
(c) (6 points) Provide a parse tree for the same term, x ∗ y + (5 − 3), using the canonical derivation. Note here that we don’t need to bother with the derivation order here, since the grammar is unambiguous – if this grammar were ambiguous, the derivation would matter, since we could get different parse trees:
F y^ E -^ T
x (^) T F
(d) (2 points, circle the answer) Is there a unique parse tree for this term? True /False If this were not true, then we would have two different ways of interpreting this term in the language.
(e) (2 points, circle the answer) Is there a unique leftmost derivation for this term? True /False If this were not true, we would have an ambiguous grammar.
(a) (10 points) Give a most general unifier for the following unification problem. Lower case letters (f, g, h, a, b, c) are constants or term constructors: specifically, f is a term constructors with arity 2, g and h are term constructors with arity 1, and a, b, and c are constant terms with arity 0. Letters α,β, δ, and γ are variables. Show your work by listing the operation performed in each step of unification – decompose, orient, delete, eliminate – and the result of the step. If unification is not possible, work as far as possible and show where unification fails. If unification does not fail, show the final substitution, which should be a set of variable to term mappings.
{f(f(α, g(b)), g(β)) = f(γ, g(a)) ; g(α) = g(h(δ)) ; f(h(δ), γ) = f(h(c), γ)} decompose {f(α, g(b)) = γ ; g(β) = g(a) ; g(α) = g(h(δ)) ; f(h(δ), γ) = f(h(c), γ)} orient {γ = f(α, g(b)) ; g(β) = g(a) ; g(α) = g(h(δ)) ; f(h(δ), γ) = f(h(c), γ)} decompose {γ = f(α, g(b)) ; β = a ; g(α) = g(h(δ)) ; f(h(δ), γ) = f(h(c), γ)} decompose {γ = f(α, g(b)) ; β = a ; α = h(δ) ; f(h(δ), γ) = f(h(c), γ)} decompose {γ = f(α, g(b)) ; β = a ; α = h(δ) ; h(δ) = h(c) ; γ = γ } delete {γ = f(α, g(b)) ; β = a ; α = h(δ) ; h(δ) = h(c) } decompose {γ = f(α, g(b)) ; β = a ; α = h(δ) ; δ = c } eliminate {γ = f(α, g(b)) ; β = a ; α = h(c) ; δ = c } eliminate {γ = f(h(c), g(b)) ; β = a ; α = h(c) ; δ = c }
FINAL {γ = f(h(c), g(b)) ; β = a ; α = h(c) ; δ = c }
(b) (2 points) Using the unifier discovered above, apply the substitution and show the final terms, which should be equalities and which should have no variables. If unification got stuck above, just write “unification failed” below.
Rules for type derivations:
Constants
⊢ n : int (assuming n is an int)
⊢ true : bool
⊢ false : bool
Variables
Γ ⊢ x : τ if(x : τ ) ∈ Γ
Arithmetic Operators Γ ⊢ e 1 : int Γ ⊢ e 2 : int Γ ⊢ e 1 ⊕ e 2 : int
(⊕ ∈ {+, −, ∗, /, · · · })
Relational Operators Γ ⊢ e 1 : int Γ ⊢ e 2 : int Γ ⊢ e 1 ∼ e 2 : bool
(∼ ∈ {<, >, ≤, ≥, =, 6 =, · · · })
Booleans Γ ⊢ e 1 : bool Γ ⊢ e 2 : bool Γ ⊢ e 1 && e 2 : bool Γ ⊢ e 1 : bool Γ ⊢ e 2 : bool Γ ⊢ e 1 || e 2 : bool Γ ⊢ e 1 : bool Γ ⊢! e 1 : bool If Γ ⊢ e 1 : bool Γ ⊢ e 2 : τ Γ ⊢ e 3 : τ Γ ⊢ if e 1 then e 2 else e 3 : τ Function Abstraction Γ ∪ [x : τ 1 ] ⊢ e : τ 2 Γ ⊢ fun x−>e : τ 1 → τ 2 Function Application Γ ⊢ e 1 : τ 1 → τ 2 Γ ⊢ e 2 : τ 1 Γ ⊢ e 1 e 2 : τ 2 Let Γ ⊢ e 1 : τ Γ ∪ [x : τ ] ⊢ e 2 : τ ′ Γ ⊢ let x = e 1 in e 2 : τ ′ Letrec Γ ∪ [x : τ ] ⊢ e 1 : τ Γ ∪ [x : τ ] ⊢ e 2 : τ ′ Γ ⊢ let rec x = e 1 in e 2 : τ ′