CS 152 - Lecture 13

Cover page image

Cay S. Horstmann

Scope

Static vs. Dynamic Scoping

Implementation of Dynamic Scoping

Implementation of Static Scoping

Implementing Recursive Functions

Lab

???

Step 1: Bash

Step 1: Bash (Continued)

  1. Make a file test1.bash with the contents
    x="2"
    
    function f {
       echo $x
    }
    
    function main {
       local x="3" ; 
       f ;
    }
    
    main
    
    .
  2. Start the bash shell. Run the program: source test1.bash. What does it print?
  3. What does that tell you about variable scoping in the bash language?

Step 2: More Bash

  1. Make a file test2.bash with the contents.
    x="2"
    
    function f {
       echo $x
    }
    
    function g {
       local x="3" ; 
       f ;
    }
    
    function main {
       local x="4" ;
       f ;
       g ;
       f ;
    }
    
    f ;
    main 
    
    

    What do you expect this program to print?

  2. Start the bash shell. Run the program: source test2.bash. What does it print?
  3. Explain the behavior by drawing diagrams of the symbol table.

Step 3: Understanding Closures in SL1

  1. Consider the SL1 program
    val a = 3;
    val f = { x => x * a };
    val g = { a => a * f(a)};
    g(1)

    What result output do you expect?

  2. Start the SL1 interpreter from the previous lab and run the program. What output did you get?
  3. Place a breakpoint in the line
    case Valdef(name, Function(params, body)) => { (name, Closure(params, body, symbols)) :: symbols }

    Run the debugger with the same program as input. When the breakpoint is hit, inspect symbols. What do you get for symbols when the definitions of f and g are evaluated?

  4. Change the code for
    case Funcall(fun, args) => eval(fun, symbols) match

    to

    case Funcall(fun, args) => val funval = eval(fun, symbols); funval match

    Debug the program again, this time with a breakpoint in the line

    evalBlock(body, params.zip(args.map(eval(_, symbols))) ::: syms)

    The breakpoint will be triggered when g and f are executed. What are the values of symbols and the syms in the closure object when g is executed?

  5. With what symbol table is the body of f executed?