Recursive Definitions, Fixed Points and the Combinator

Similar documents
Part I. Historical Origins

Introduction to the l-calculus

Fundamentals and lambda calculus

Functions as data. Massimo Merro. 9 November Massimo Merro The Lambda language 1 / 21

COMP 1130 Lambda Calculus. based on slides by Jeff Foster, U Maryland

One of a number of approaches to a mathematical challenge at the time (1930): Constructibility

Fundamentals and lambda calculus. Deian Stefan (adopted from my & Edward Yang s CSE242 slides)

A Quick Overview. CAS 701 Class Presentation 18 November Department of Computing & Software McMaster University. Church s Lambda Calculus

Introduction to Lambda Calculus. Lecture 7 CS /08/09

Pure Lambda Calculus. Lecture 17

CITS3211 FUNCTIONAL PROGRAMMING

Organization of Programming Languages CS3200/5200N. Lecture 11

Lecture 5: The Untyped λ-calculus

Introduction to Lambda Calculus. Lecture 5 CS 565 1/24/08

Lambda Calculus. Lambda Calculus

Last class. CS Principles of Programming Languages. Introduction. Outline

Harvard School of Engineering and Applied Sciences CS 152: Programming Languages. Lambda calculus

Lambda Calculus. Lecture 4 CS /26/10

Lambda Calculus. Variables and Functions. cs3723 1

Introduction to the Lambda Calculus

Programming Language Features. CMSC 330: Organization of Programming Languages. Turing Completeness. Turing Machine.

CMSC 330: Organization of Programming Languages

11/6/17. Outline. FP Foundations, Scheme. Imperative Languages. Functional Programming. Mathematical Foundations. Mathematical Foundations

5. Introduction to the Lambda Calculus. Oscar Nierstrasz

λ calculus Function application Untyped λ-calculus - Basic Idea Terms, Variables, Syntax β reduction Advanced Formal Methods

CMSC 330: Organization of Programming Languages

Lambda Calculus alpha-renaming, beta reduction, applicative and normal evaluation orders, Church-Rosser theorem, combinators

dynamically typed dynamically scoped

Elixir, functional programming and the Lambda calculus.

Functional Programming

CS 6110 S14 Lecture 1 Introduction 24 January 2014

The Untyped Lambda Calculus

Type Systems Winter Semester 2006

CMSC 330: Organization of Programming Languages. Lambda Calculus

Lambda Calculus.

9/23/2014. Why study? Lambda calculus. Church Rosser theorem Completeness of Lambda Calculus: Turing Complete

Lambda Calculus and Type Inference

CMSC 330: Organization of Programming Languages

INF 212 ANALYSIS OF PROG. LANGS LAMBDA CALCULUS. Instructors: Crista Lopes Copyright Instructors.

CMSC 330: Organization of Programming Languages. Lambda Calculus

Introductory Example

VU Semantik von Programmiersprachen

lambda calculus History 11/28/13 Jianguo Lu A formal system designed to inves:gate func:on defini:on, func:on applica:on, and recursion.

Overview. A normal-order language. Strictness. Recursion. Infinite data structures. Direct denotational semantics. Transition semantics

Formal Semantics. Aspects to formalize. Lambda calculus. Approach

Functional Programming and λ Calculus. Amey Karkare Dept of CSE, IIT Kanpur

COMP80 Lambda Calculus Programming Languages Slides Courtesy of Prof. Sam Guyer Tufts University Computer Science History Big ideas Examples:

Pure (Untyped) λ-calculus. Andrey Kruglyak, 2010

Introduction to the λ-calculus

Lambda Calculus. Adrian Groza. Department of Computer Science Technical University of Cluj-Napoca

Activity. CSCI 334: Principles of Programming Languages. Lecture 4: Fundamentals II. What is computable? What is computable?

CSCI.4430/6969 Programming Languages Lecture Notes

The Untyped Lambda Calculus

Functional Programming

CS 209 Functional Programming

Programming Languages

Functional Programming Languages (FPL)

Introduction to the Lambda Calculus. Chris Lomont

CS 4110 Programming Languages & Logics. Lecture 17 Programming in the λ-calculus

CSE 505: Concepts of Programming Languages

The Untyped Lambda Calculus

Functional Languages and Higher-Order Functions

CIS 500 Software Foundations Fall September 25

COP4020 Programming Languages. Functional Programming Prof. Robert van Engelen

Constraint-based Analysis. Harry Xu CS 253/INF 212 Spring 2013

10.6 Theoretical Foundations

λ calculus is inconsistent

Lexicografie computationala Feb., 2012

CMSC330. Objects, Functional Programming, and lambda calculus

Programming Language Concepts: Lecture 19

> module Lambda where > import Data.List -- I need some standard list functions

1.3. Conditional expressions To express case distinctions like

From the λ-calculus to Functional Programming Drew McDermott Posted

Week 4: Functional Programming

Computer Science 203 Programming Languages Fall Lecture 10. Bindings, Procedures, Functions, Functional Programming, and the Lambda Calculus

CSE 505. Lecture #9. October 1, Lambda Calculus. Recursion and Fixed-points. Typed Lambda Calculi. Least Fixed Point

CS 242. Fundamentals. Reading: See last slide

Chapter 5: The Untyped Lambda Calculus

Untyped Lambda Calculus

Recursion. Lecture 6: More Lambda Calculus Programming. Fixed Points. Recursion

Lambda Calculus and Extensions as Foundation of Functional Programming

More Untyped Lambda Calculus & Simply Typed Lambda Calculus

Foundations. Yu Zhang. Acknowledgement: modified from Stanford CS242

Programming Language Pragmatics

1 Scope, Bound and Free Occurrences, Closed Terms

n λxy.x n y, [inc] [add] [mul] [exp] λn.λxy.x(nxy) λmn.m[inc]0 λmn.m([add]n)0 λmn.n([mul]m)1

Untyped Lambda Calculus

Formal Systems and their Applications

CSCE 314 TAMU Fall CSCE 314: Programming Languages Dr. Flemming Andersen. Haskell Functions

Lambda Calculus-2. Church Rosser Property

Homework. Lecture 7: Parsers & Lambda Calculus. Rewrite Grammar. Problems

The Lambda Calculus. 27 September. Fall Software Foundations CIS 500. The lambda-calculus. Announcements

Lecture 9: More Lambda Calculus / Types

- M ::= v (M M) λv. M - Impure versions add constants, but not necessary! - Turing-complete. - true = λ u. λ v. u. - false = λ u. λ v.

CSC312 Principles of Programming Languages : Functional Programming Language. Copyright 2006 The McGraw-Hill Companies, Inc.

CSE 3302 Programming Languages Lecture 8: Functional Programming

CMPUT 325 : Lambda Calculus Basics. Lambda Calculus. Dr. B. Price and Dr. R. Greiner. 13th October 2004

Functional Languages. Hwansoo Han

Concepts of programming languages

Urmas Tamm Tartu 2013

Transcription:

Recursive Definitions, Fixed Points and the Combinator Dr. Greg Lavender Department of Computer Sciences University of Texas at Austin Recursive Self-Reference Recursive self-reference occurs regularly it has been studied extensively within the context of logic & computability S. Kleene, W.V.O. Quine, R. Smullyan, etc. Kleene s Recursion Theorem fundamental theorem in computability Fixed Point Theory fixed point operators Y combinator 2/7/05 2 1

Recursive Definition Computable functions are often defined recursively. how do we define them syntactically? need a way to deal with the issue of self-referential naming as part of writing down a function definition. can t define something in terms of itself without some mechanism to escape from the apparent infinite loop Example: let fact n = if (n == 0) then 1 else n * fact(n-1) in fact(5); there is a technical syntactic definitional problem with this recursive expression we cannot define the name fact in terms of itself because the expression will never be completed statically: We don t know how far to unroll the definition unless we run it recursive self-reference introduces a challenge to the language designer and compiler/interpreter implementer 2/7/05 3 Recursive Definition To illustrate the recursive definition problem more practically, consider the problem of writing a program in some language that prints a copy of itself when evaluated. let s try it with C: main() {printf( main() {printf( main() ); } how do you complete the program? you have to have some mechanism for escaping out of the infinite recursive definition usually there is some trick that is employed that uses some form of syntactic escape 2/7/05 4 2

Syntactic Escape Tricks A quine is a program that prints an exact syntactic copy of itself. an interesting exercise is to try to write the shortest quine in a variety of languages; for example: A C quine in 65 characters: main(a){printf(a="main(a){ printf(a=%c%s%c,34,a,34);}",34,a,34);} A Scheme quine in 46 characters: ((lambda(x) `(,x ',x)) '(lambda(x) `(,x ',x))) A λ-calculus quine in 14 characters: (λx.xx)(λx.xx) For more examples, see http://www.nyx.net/~gthompso/quine.htm 2/7/05 5 Lambda Calculus A formal notation for expressing computable functions lambda definability the class of functions definable in the lambda calculus are exactly the computable functions led to Church to state his famous thesis: λ-calculus <=> Turing Machines <=> Church-Turing thesis 2/7/05 6 3

Various Function Notations Set Theoretic: {(x,y) Vx,y ε N: y = x 2 } Algebraic: f: N->N f(x) = x 2 ; Type-free λ-notation: λx.x * x Typed λ-notation: λx:int.x * x Polymorphic λ-notation: λx:α.x * x Scheme: (define square (lambda (x) (* x x))) Algol-60: integer procedure square(x); integer x; begin square := x * x end; Pascal: function square (x:integer) : integer; begin square := x * x end; K&R C: square(x) int x; { return (x * x); } StdC/C++/Java: int square(int x) { return (x * x); } ML97: fun square x = x * x; fun square (x:int) = x * x; val square = fn x => x * x; Haskell: square :: Int->Int square x = x * x map (\x -> x * x) [0..] [(x,y) x <- [0..], y <- [x * x]] 2/7/05 7 Uses of the λ-calculus A formal notation, theory, and model of computation Conceptual foundation for functional programming ISWIM, Lisp, Scheme, ML, Haskell, Natural model for many programming constructs higher-order functions, variables, block scopes, expressions, ordered pairs, lists, records, recursion calling conventions: call-by-value, call-by-need, call-by-name Type inferencing & polymorphic type systems Hindley-Milner type system Notation for Scott-Strachey denotational semantics domain theory of Dana Scott 2/7/05 8 4

Definitions λ-calculus is a formal notation for defining functions expressions in this notation are called λ-expressions every λ-expression denotes a function that is out there in the platonistic sense a λ-expression consists of 3 kinds of terms: variables: x,y,z, etc. we use V, V 1, V 2, etc., for arbitrary variables abstractions: λv.e Where V is some variable and E is another λ-term applications: (E 1 E 2 ) Where E 1 and E 2 are λ-terms applications are sometimes called combinations 2/7/05 9 Formal Syntax in BNF <λ-term> ::= <variable> λ <variable>. <λ-term> (<λ-term> <λ-term>) <variable> ::= x y z Or, more compactly: E ::= V λv.e (E 1 E 2 ) V :: = x y z Where V is an arbitrary variable and E i is an arbitrary λ-expression. We call λv the head of the λ-expression and E the body. 2/7/05 10 5

Variables variables can be bound or free the λ-calculus assumes an infinite universe of free variables they are bound to functions in an environment they become bound by usage in an abstraction for example, in the λ-expression: λx.x*y x is bound by λ over the body x * y, but y is a free variable. I.e., lexically scoped. Compare this to scheme: (define z 3) (define x 2) (define y 2) (define multi-by-y (lambda (x) (* x y))) (multi-by-y z) => 6 2/7/05 11 Abstractions if λv.e is an abstraction V is a bound variable over the body E it denotes the function that when given an actual argument a, evaluates to the function E with all occurrences of V in E replaced with a, written E[a/V] For example the abstraction: λx.x is the identity function that can be applied to either values or other lambda abstractions: (λx.x)1 => 1 (λx.x)a => a (λx.x)(λx.x) => (λx.x) 2/7/05 12 6

Applications If E 1 and E 2 are λ-expressions, so is (E 1 E 2 ) application is basically function evaluation apply the function E 1 to the argument E 2 E 1 is called the rator (ope-rator) E 2 is called the rand (ope-rand) For example: (λx.xx) 1 => 11 (λx.xx) a => aa (λx.xx)(λx.xx) => (λx.xx)(λx.xx) this last example is a quine and it doesn t terminate. It keeps duplicating itself ad infinitum. In this example, we don t care, but in real programming we do care about non-terminating evaluations. 2/7/05 13 Conversion/reduction rules α-conversion: any abstraction λv.e can be converted to λv.e[v /V] iff [V /V] in E is valid β-conversion (β-reduction): any application (λv.e 1 ) E 2 can be converted to E 1 [E 2 /V] iff [E 2 /V] in E 1 is valid η-conversion: any abstraction λv.(e V) where V has no free occurrences in E can be converted to E 2/7/05 14 7

Conversion rule notation α E 1 E 2 β E 1 E 2 η E 1 E 2 bound variable renaming to avoid naming conflicts like a function call evaluation elimination of irrelevant information 2/7/05 15 α-redex α-reduction is bound variable renaming α E 1 E applied to an α-redex iff no naming 2 conflicts redex = reducible expression λx.x α λy.y (λx.x)[y/x] λx.f x α λy.f y (λx.f x)[y/x] λx.λy.x+y α λy.λy.f y+y not valid since y is already a bound variable in E 1 2/7/05 16 8

β-redex β E 1 E 2 (λx.f x) E β f E (λx.(λy. x + y)) 3 β (λy.3 + y) 4 β 3 + 4 λy.3 + y 2/7/05 17 Fixed Points A fixed point is a value x in the domain of a function that is the same in the co-domain f(x). every value in the domain of the identity function is a fixed point λx.x = x can you think of others? factorial(1) = 1 fibonacci(0) = 0, fibonacci(1) = 1 square(0) = 0, square(1) = 1 abs(x) = x, if x >= 0 sin(0) = 0 functionals may also have fixed points D x (e x ) = e x 2/7/05 18 9

Fixed Point Operators Consider a fixed point operator Fix such that F (Fix F) = Fix F or equivalently Fix F = F (Fix F) Fix is a function that takes any function f an argument and then repeats the function f applied to (Fix F) there are many such fixed point operators The lazy Y combinator is a fixed point operator Y = (λf. (λx.f(x x)) (λx.f(x x))) Y F = (λf. (λx.f(x x)) (λx.f(x x))) F => (λx.f(x x)) (λx.f(x x)) => F (λx.f(x x)) (λx.f(x x)) => F (Y F) 2/7/05 19 Using the lazy Y combinator Any expression of the form f x 1 x n = E is called recursive if f occurs free in E if you want: f x 1 x n = ~~~~ f ~~~~ then define F = Y (λf x 1 x n. ~~~~ f ~~~~) for example: fact n = if (n==0) then 1 else n * fact(n-1) Becomes F = λf n. if (n==0) then 1 else n * f(n-1) fact = Y F fact 2 = (Y F) 2 => F (Y F) 2 => F fact 2 => (λf n.if (n==0) then 1 else n * f(n-1)) fact 2 => (if (2==0) then 1 else n * fact(2-1)) => (if (2==0) then 1 else n * (Y F)(1)) => (if (2==0) then 1 else n * ((λf n.if (n==0) then 1 else n * f(n-1)) fact 1 => 2/7/05 20 10

Implementing Fix in Haskell The lazy Y combinator can only be implemented in a language that supports lazy (non-strict) evaluation Haskell allows this: fix f = f (fix f) fact :: Integer->Integer fact = fix (\f n -> if n==0 then 1 else n*f (n-1)) fact 5 => 120 2/7/05 21 More Fix Examples in Haskell greatest common divisor gcd :: Integral a => a -> a -> a gcd = fix (\f x y -> case (abs x, abs y) of (x,0) -> x (x,y) -> f y (x `rem` y)) map function map :: (a->b) -> [a] -> [b] map = fix (\f g xs -> case xs of [] -> [] (x:xs) -> g x : f g xs) foldl function foldl :: (a -> b -> a) -> a -> [b] -> a foldl = fix (\f g z xs -> case xs of [] -> z (x:xs) -> f g (g z x) xs) 2/7/05 22 11

Lazy Y Combinator in Scheme We can write the Y combinator in Scheme: (define Y (lambda (f) ((lambda (x) (f (x x))) (lambda (x) (f (x x)))))) but it results in an infinite loop if we try to define a recursive function with it! we cannot use the lazy Y combinator in a language with eager (strict) evaluation order the problem is with the last lambda expression 2/7/05 23 Eager Fixed Point Combinator Due to Turing Y eager = (λx y. y (x x y)) (λx y. y (x x y)) We can translate this into Scheme and use it to define (curried) recursive functions: (define Y (lambda (f) ((lambda (x) (f (lambda (y) ((x x) y))) (lambda (x) (f (lambda (y) ((x x) y))))))) (define fact (Y (lambda (f) (lambda (n) (if (zero? n) 1 (* n (f (- n 1)))))))) 2/7/05 24 12

Modified Turing Combinator We can simplify the previous definition of Y by recognizing that we don t need to delay the evaluation of the first lambda expression (define T (lambda (f) ((lambda (x) (f (x x))) (lambda (x) (f (lambda (y) ((x x) y))))))) 2/7/05 25 Named Let and Letrec In Scheme, the named let is used to define a local recursive function: (define fact (lambda (n) (let tfact ((n n) (m 1)) (if (zero? N) 1 (tfact (- n 1) (* m n)))))) Named let is just a macro using letrec, which appears to be a sugared fixed point operator (let name ((var val)..) exp1 exp2 ) ((letrec ((name (lambda (var ) exp1 exp2 ))) name) val ) 2/7/05 26 13

For Further Study 1. Chris Hankin, An Introduction to Lambda Calculi for Computer Scientists, Kings College London Press, 2004. 2. Raymond Smullyan, Diagonalization and Self-Reference, Oxford University Press, 1994. 3. Douglas Hofstadter, Godel, Escher, Bach: An Eternal Golden Braid, 20 th Anniv Edition, Basic Books, 1999. 4. Don Blaheta, The Lambda Calculus, see paper on course website. 5. Richard Gabriel, The Why of Y, see paper on course website. 2/7/05 27 14