First Order Functions
@PL on
We are defining F1VAE
, arithmetic expressions with first order functions. We are explicitly definig the functions using def
keywords, and store the definition in another storage, FEnv
.
The following code is for defining the function.
enum FunDef {
case FD(String, String, Expr)
}
FEnv
, the new storage for function definitions is a map from function name to its definition.
typealias FEnv = [String : FunDef]
The new definition of Expr
includes function call, designated by its name and an expression for a single parameter.
enum Expr: prevExpr {
// includes all the former definition
case Call(String, Expr) //fof
}
Interpretation implementation.
func interp(_ e: Expr, _ env: Env, _ fenv: FEnv) -> Value
{
switch e {
case .Num(let n):
return .NumV(n)
case .Add(let l, let r):
return NumVOperation(ADD, interp(l, env, fenv), interp(r, env, fenv))
case .Sub(let l, let r):
return NumVOperation(SUB, interp(l, env, fenv), interp(r, env, fenv))
case .Val(let x, let i, let b):
return interp(b, env + [x : interp(i, env, fenv)], fenv)
case .Id(let x):
return env[x]!
case .Call(let f, let a):
switch fenv[f]! { // lookup(f, fenv)]
case .FD(_, let pname, let body):
let v = interp(a, env, fenv)
return interp(body, [pname : v], fenv) // static scoping
return interp(body, env + [pname : v], fenv) // dynamic scoping
}
}
}
All the materials are from CS320 class held on 2021 spring, KAIST.