Closures

the best idea in PL design?

Daniel Jackson

The Problem: Controlling Scope

  • Want to minimize scope of variables
  • Scope qualifiers help, but aren't enough
  • Prototype class pattern is broken

Minimizing Scope

  • A general principle: minimize the scope of all vars
  • A "need to know" policy for variables
  • Remove let and see what happens

Stateful Functions

  • What if function maintains state across calls?
  • With let, can make this work for one function
  • How about a family of functions (eg, methods)?

Prototyping Breaks Encapsulation

  • Representation is exposed!
  • How to limit the scope of bal to the methods?

Thinking about Scope

  • What exactly are the scoping rules?
  • Let's look at some trickier examples

Tricky Example #1

  • Which greeting variable does call to greet use?
  • Dynamic scoping: the one in the context of the call
  • Lexical scoping: the one in the context of the declaration

Tricky Example #2

  • How the heck does this work?

How Lexical Scoping Works

  • When a function is created, it retains a link to the environment
  • When a function is executed, it uses that original environment
  • ... augmented with the argument bindings

Data Abstraction

  • A pattern for abstract types
  • Using closures to encapsulate the rep

A bank account

  • Can you rob this bank?

A mutable set

  • A pattern for data abstraction: methods access local var
  • Closures provide encapsulation (cf. prototype methods)

Some refinements

  • Attach a type using prototypes
  • Freeze slots to prevent methods being mutated

A cool example

  • Using a functional to change a function's performance

Fibonacci

  • Classic function, returns fibonacci number
  • Try incrementing argument and note performance

Timing a function

  • Let's time it, with a functional (of course)

A memoizing functional

  • Takes a function & returns a memoizing version
  • Apply to Fibonacci: can we do better?
  • Exercise: what if you inline the expr for mfib?

Memoizing Fibonacci

  • Apply memoizing to internal calls too
  • Now linear, no longer exponential!

Closure puzzles

  • Test yourself: how well do you understand closures?
  • Bonus: a subtlety of let vs. var

One free x

  • What does f() evaluate to?

Another free x

  • What does f() evaluate to?

Modifying arguments

  • What does x evaluate to at the end?

Multipliers

  • Can you guess what multipliers was supposed to return?
  • What does multipliers actually return? Why?
  • What happens if you replace var by let? Why?

THE END