Fall Semester, Lecture Notes { November 12, Variations on a Scheme Nondeterministic evaluation

Similar documents
Fall Semester, The Metacircular Evaluator. Today we shift perspective from that of a user of computer langugaes to that of a designer of

Scheme in Scheme: The Metacircular Evaluator Eval and Apply

Streams, Delayed Evaluation and a Normal Order Interpreter. CS 550 Programming Languages Jeremy Johnson

The Eval/Apply Cycle Eval. Evaluation and universal machines. Examining the role of Eval. Eval from perspective of language designer

6.184 Lecture 4. Interpretation. Tweaked by Ben Vandiver Compiled by Mike Phillips Original material by Eric Grimson

Why do we need an interpreter? SICP Interpretation part 1. Role of each part of the interpreter. 1. Arithmetic calculator.

Discussion 12 The MCE (solutions)

6.037 Lecture 4. Interpretation. What is an interpreter? Why do we need an interpreter? Stages of an interpreter. Role of each part of the interpreter

regsim.scm ~/umb/cs450/ch5.base/ 1 11/11/13

Review Analyzing Evaluator. CS61A Lecture 25. What gets returned by mc-eval? (not analyzing eval) REVIEW What is a procedure?

Deferred operations. Continuations Structure and Interpretation of Computer Programs. Tail recursion in action.

Parsing Scheme (+ (* 2 3) 1) * 1

Syntactic Sugar: Using the Metacircular Evaluator to Implement the Language You Want

An Explicit-Continuation Metacircular Evaluator

CS 314 Principles of Programming Languages. Lecture 16

This exam is worth 30 points, or 18.75% of your total course grade. The exam contains

Lexical vs. Dynamic Scope

Functional Programming. Pure Functional Programming

6.037 Lecture 7B. Scheme Variants Normal Order Lazy Evaluation Streams

Administrivia. Simple data types

From Syntactic Sugar to the Syntactic Meth Lab:

This exam is worth 70 points, or about 23% of your total course grade. The exam contains 15 questions.

Building up a language SICP Variations on a Scheme. Meval. The Core Evaluator. Eval. Apply. 2. syntax procedures. 1.

CS61A Discussion Notes: Week 11: The Metacircular Evaluator By Greg Krimer, with slight modifications by Phoebus Chen (using notes from Todd Segal)

Turtles All The Way Down

Computer Science 21b (Spring Term, 2015) Structure and Interpretation of Computer Programs. Lexical addressing

CS 314 Principles of Programming Languages

Building a system for symbolic differentiation

6.001, Spring Semester, 1998, Final Exam Your Name: 2 Question 1 (12 points): Each of the parts below should be treated as independent. For each part,

CS61A Midterm 2 Review (v1.1)

Normal Order (Lazy) Evaluation SICP. Applicative Order vs. Normal (Lazy) Order. Applicative vs. Normal? How can we implement lazy evaluation?

CS61A Summer 2010 George Wang, Jonathan Kotker, Seshadri Mahalingam, Eric Tzeng, Steven Tang

6.001, Spring Semester, 1998, Final Exam Solutions Your Name: 2 Part c: The procedure eval-until: (define (eval-until exp env) (let ((return (eval-seq

Interpreters and Tail Calls Fall 2017 Discussion 8: November 1, 2017 Solutions. 1 Calculator. calc> (+ 2 2) 4

Sample Final Exam Questions

Fall 2018 Discussion 8: October 24, 2018 Solutions. 1 Introduction. 2 Primitives

Summer 2017 Discussion 10: July 25, Introduction. 2 Primitives and Define

User-defined Functions. Conditional Expressions in Scheme

4.2 Variations on a Scheme -- Lazy Evaluation

6.001: Structure and Interpretation of Computer Programs

CS 314 Principles of Programming Languages

Below are example solutions for each of the questions. These are not the only possible answers, but they are the most common ones.

Procedural abstraction SICP Data abstractions. The universe of procedures forsqrt. Procedural abstraction example: sqrt

CS 61A Interpreters, Tail Calls, Macros, Streams, Iterators. Spring 2019 Guerrilla Section 5: April 20, Interpreters.

(scheme-1) has lambda but NOT define

Fall 2017 Discussion 7: October 25, 2017 Solutions. 1 Introduction. 2 Primitives

Project 2: Scheme Interpreter

A Brief Introduction to Scheme (II)

CSc 520 Principles of Programming Languages

Building a system for symbolic differentiation

CS 360: Programming Languages Lecture 10: Logic Programming with Prolog

1.3. Conditional expressions To express case distinctions like

Chapter 1. Fundamentals of Higher Order Programming

Documentation for LISP in BASIC

Principles of Programming Languages

An introduction to Scheme


INTERPRETERS 8. 1 Calculator COMPUTER SCIENCE 61A. November 3, 2016

Basic Scheme February 8, Compound expressions Rules of evaluation Creating procedures by capturing common patterns

Principles of Programming Languages

C311 Lab #3 Representation Independence: Representation Independent Interpreters

Evaluating Scheme Expressions

6.001 Notes: Section 8.1

Principles of Programming Languages 2017W, Functional Programming

Intro. Scheme Basics. scm> 5 5. scm>

Introduction to Scheme

Spring 2018 Discussion 7: March 21, Introduction. 2 Primitives

MORE SCHEME. 1 What Would Scheme Print? COMPUTER SCIENCE MENTORS 61A. October 30 to November 3, Solution: Solutions begin on the following page.

An Explicit Continuation Evaluator for Scheme

Scheme: Strings Scheme: I/O

Announcements. The current topic: Scheme. Review: BST functions. Review: Representing trees in Scheme. Reminder: Lab 2 is due on Monday at 10:30 am.

LECTURE 16. Functional Programming

Code example: sfact SICP Explicit-control evaluator. Example register machine: instructions. Goal: a tail-recursive evaluator.

Repetition Through Recursion

Delayed Expressions Fall 2017 Discussion 9: November 8, Iterables and Iterators. For Loops. Other Iterable Uses

CS1 Recitation. Week 2

61A LECTURE 18 SCHEME. Steven Tang and Eric Tzeng July 24, 2013

Programming Languages

SCHEME 8. 1 Introduction. 2 Primitives COMPUTER SCIENCE 61A. March 23, 2017

Typed Racket: Racket with Static Types

Scheme. Functional Programming. Lambda Calculus. CSC 4101: Programming Languages 1. Textbook, Sections , 13.7

An Introduction to Scheme

6.001, Fall Semester, 1998 Lecture Notes, October 27 { Object Oriented Programming 2 An environment diagram illustrating +define foo +cons 1 2,, +set-

1. For every evaluation of a variable var, the variable is bound.

SCHEME 10 COMPUTER SCIENCE 61A. July 26, Warm Up: Conditional Expressions. 1. What does Scheme print? scm> (if (or #t (/ 1 0)) 1 (/ 1 0))

Recursive Functions of Symbolic Expressions and Their Computation by Machine Part I

Using Symbols in Expressions (1) evaluate sub-expressions... Number. ( ) machine code to add

CS450 - Structure of Higher Level Languages

CS61A Notes Week 6: Scheme1, Data Directed Programming You Are Scheme and don t let anyone tell you otherwise

SCHEME 7. 1 Introduction. 2 Primitives COMPUTER SCIENCE 61A. October 29, 2015

Lisp. Versions of LISP

Recursive Functions of Symbolic Expressions and Their Application, Part I

CS 61A Discussion 8: Scheme. March 23, 2017

Functional Programming. Big Picture. Design of Programming Languages

COP4020 Programming Languages. Functional Programming Prof. Robert van Engelen

Berkeley Scheme s OOP

Comp 311: Sample Midterm Examination

Functions, Conditionals & Predicates

Modern Programming Languages. Lecture LISP Programming Language An Introduction

Fall Semester, Lecture Notes { September 26, Today's lecture will use the Henderson Picture Language as an example of how we can merge

Transcription:

1 MASSACHUSETTS INSTITUTE OF TECHNOLOGY Department of Electrical Engineering and Computer Science 6.001 Structure and Interpretation of Computer Programs Fall Semester, 1996 Lecture Notes { November 12, 1996 Variations on a Scheme Nondeterministic evaluation In todays lecture, we are going to discuss another variation on the idea of an evaluator, in this case introducing the idea of nondeterminism. Nondeterminism can be introduced into Scheme with the new special form amb. The idea is that when the interpreter reaches an expression of the form (amb e 1 e 2 ) it nondeterministically selects one of expressions e 1 or e 2 and continues the evaluation with that expression. Since the language with amb is nondeterministic, a given expression can have many dierent possible executions and many dierent possible values. In general, the special form amb can take anynumber of arguments, one of which is nondeterministically selected at run time. As an example consider (define (a-number-between low high) (cond ((= low high) low) (else (amb low (a-number-between (+ low 1) high))))) The expression (a-number-between 1 10) has ten dierent possible values, each of which is an integer between 1 and 10. Consider the following procedure. (define (a-pythagorean-triple-between low high) (let ((n (a-number-between low high)) (m (a-number-between low high)) (p (a-number-between low high))) (cond ((= (+ (* n n) (* m m)) (* p p)) (list n m p)) (else (amb))))) The expression (a-pythagorean-triple-between 1 10) has 1000 dierent possible executions. All but four of these executions fail. The four non-failing executions have values (3 4 5), (4 3 5), (6 8 10), and (8 6 10). In general, if (n m p) is a non-failing value of the expression (a-pythagorean-triple-between low high) then n, m, and p are numbers between low and high such that n 2 + m 2 = p 2. In other words, there exists a right triangle whose sides have length n, m, and p. One way to solve such problems is to exhaustively search out all possibilities, ltering out those that violate some constraint. We can express the requirement that a particular predicate expression p is true by requireing its truth:

6.001, Fall Semester, 1996 Lecture Notes { November 12, 1996 2 (define (require p) (cond ((not p) (amb)) (else 'ok))) (define (a-pythagorean-triple-between low high) (let ((n (a-number-between low high)) (m (a-number-between low high)) (p (a-number-between low high))) (require (= (+ (* n n) (* m m)) (* p p))) (list n m p))) We are often interested in determining whether or not a given nondeterministic expression has a nonfailing value. One might try running the probabilistic interpreter over and over again hoping to nd a nonfailing value. Amuch better approach istosystematically search the space of all possible executions. We will play with a modied version of the evaluator which we call the search evaluator. The search evaluator systematically searches the space of all possible executions of a given expression. When the search evaluator encounters an application of amb it initially selects the rst argument. If this selection does not result in a nonfailing execution, then the evaluator \backs up" and tries the second argument. The search evaluator is used to implement a read-eval-print loop with some unusual properties. The read-eval-print loop reads an expression and prints the value of the rst nonfailing execution. For example, consider the following interaction. SEARCH==>> (a-number-between 1 10) Starting a new problem 1 SEARCH==>> (a-pythagorean-triple-between 1 10) Starting a new problem (3 4 5) The read-eval-print loop allows the user to ask for alternative executions of an expression. If the rst execution is not desired, or if one simply wants to see the value of the next successful execution, one can ask the interpreter to back up and attempt to generate a second nonfailing execution. An example where searching over possible evaluations is useful is given by the following elementary logic puzzle: Multiple Dwelling 1 Baker, Cooper, Fletcher, Miller, and Smith live on dierent oors of an apartment house that contains only ve oors. Baker does not live on the top oor. Cooper does not live on the bottom oor. Fletcher does not live on either the top or the bottom oor. Miller lives on a higher oor than does Cooper. Smith does not live on a oor adjacent to Fletcher's. Fletcher does not live on a oor adjacent to Cooper's. Where does everyone live? In this case, we can consider possible assignments of the characters to oors in a building. We will also need to be able to tell when a list is made up of distinct entries (no two are the same): 1 This puzzle is typical of a large class of puzzles. This particular one is quoted from Superior Mathematical Puzzles, by Howard P. Dinesman, 1968, Simon and Schuster, New York.

6.001, Fall Semester, 1996 Lecture Notes { November 12, 1996 3 (define (distinct list) (cond ((null? list) true) ((null? (cdr list)) true) ((member (car list) (cdr list)) false) (else (distinct (cdr list))))) (define (multiple-dwelling) (let ((baker (amb 1 2 3 4 5)) (cooper (amb 1 2 3 4 5)) (fletcher (amb 1 2 3 4 5)) (miller (amb 1 2 3 4 5)) (smith (amb 1 2 3 4 5))) ;; Beginning of filtration (require (distinct (list baker cooper fletcher miller smith))) (require (not (= baker 5))) (require (not (= cooper 1))) (require (not (= fletcher 5))) (require (not (= fletcher 1))) (require (> miller cooper)) (require (not (= (abs (- smith fletcher)) 1))) (require (not (= (abs (- fletcher cooper)) 1))) (list (list 'baker baker) (list 'cooper cooper) (list 'fletcher fletcher) (list 'miller miller) (list 'smith smith)))) Indeed, we can try it: SEARCH==>> (multiple-dwelling) ((baker 3) (cooper 2) (fletcher 4) (miller 5) (smith 1)) SEARCH==>> (next) There are no more values of (multiple-dwelling) Below is code to implement this idea, which we will discuss. All of this is taken from the notes. (define (analyze exp) (cond ((self-evaluating? exp) (analyze-self-evaluating exp)) ((quoted? exp) (analyze-quoted exp)) ((variable? exp) (analyze-variable exp)) ((assignment? exp) (analyze-assignment exp)) ((definition? exp) (analyze-definition exp)) ((if? exp) (analyze-if exp)) ((lambda? exp) (analyze-lambda exp)) ((begin? exp) (analyze-sequence (begin-actions exp))) ((amb? exp) (analyze-amb exp)) ((cond? exp) (analyze (COND->IF exp))) ((let? exp) (analyze (LET->combination exp))) ((application? exp) (analyze-application exp)) (else (error "Unknown expression type -- ANALYZE" exp))))

6.001, Fall Semester, 1996 Lecture Notes { November 12, 1996 4 (define (analyze-self-evaluating exp) (succeed exp ) (define (analyze-quoted exp) (let ((qval (text-of-quotation exp))) (succeed qval )) (define (analyze-variable exp) (succeed (lookup-variable-value exp ) ) (define (analyze-lambda exp) (let ((vars (lambda-parameters exp)) (bproc (analyze-sequence (lambda-body exp)))) (succeed (make-procedure vars bproc ) )) (define (analyze-definition exp) (let ((var (definition-variable exp)) (vproc (analyze (definition-value exp)))) (vproc (lambda (val fail) (define-variable! var val ) (succeed 'done )) (define (analyze-assignment exp) (let ((var (assignment-variable exp)) (vproc (analyze (assignment-value exp)))) (vproc (lambda (val fail) ; *1* (let ((oval (lookup-variable-value var ))) (set-variable-value! var val ) (succeed 'done (lambda () ; *2* (set-variable-value! var oval ) ())) ))

6.001, Fall Semester, 1996 Lecture Notes { November 12, 1996 5 (define (analyze-if exp) (let ((pproc (analyze (if-predicate exp))) (cproc (analyze (if-consequent exp))) (aproc (analyze (if-alternative exp)))) (pproc (lambda (pval fail) (if (true? pval) (cproc succeed fail) )) (define (analyze-sequence exps) (define (sequentially a b) (a (lambda (va fail) (b ) succeed (aproc succeed ) (let ((procs (map analyze exps))) (if (null? procs) (error "BEGIN requires subexpressions -- ANALYZE" exps)) (define (loop first rest) (if (null? rest) first (loop (sequentially first (car rest)) (cdr rest)))) (loop (car procs) (cdr procs)))) The amb special form is the key element in the nondeterministic language. Here we see the essence of the interpretation process. The execution procedure for amb denes a loop try-next that cycles through the execution procedures for the alternative values of the amb expression. An alternative execution procedure is called with the success continuation of the amb expression, and a failure continuation that tries the next alternative. When there are no more alternatives to try, the amb expression fails. (define (analyze-amb exp) (let ((alternatives (map analyze (operands exp)))) (define (try-next alternatives) (if (null? alternatives) (fail) ((car alternatives) succeed (lambda () (try-next (cdr alternatives)))))) (try-next alternatives))))

6.001, Fall Semester, 1996 Lecture Notes { November 12, 1996 6 (define (analyze-application exp) (let ((fproc (analyze (operator exp))) (aprocs (map analyze (operands exp)))) (fproc (lambda (proc fail) (evlist aprocs (lambda (args fail) (exapply proc args succeed )) (define (exapply proc args succeed fail) (cond ((primitive-procedure? proc) (succeed (apply-primitive-procedure proc args) ((compound-procedure? proc) ((procedure-body proc) (extend-ironment (procedure-parameters proc) succeed (else args (procedure-ironment proc)) (error "Unknown procedure type -- RTAPPLY" proc)))) (define (evlist operands succeed fail) (if (null? operands) (succeed '() fail) ((car operands) (lambda (arg fail) (evlist (cdr operands) ) (lambda (args fail) (succeed (cons arg args)