Tuples. CMSC 330: Organization of Programming Languages. Examples With Tuples. Another Example

Similar documents
Background. CMSC 330: Organization of Programming Languages. Useful Information on OCaml language. Dialects of ML. ML (Meta Language) Standard ML

Anonymous Functions CMSC 330: Organization of Programming Languages

CMSC 330: Organization of Programming Languages. OCaml Higher Order Functions

CMSC 330: Organization of Programming Languages. OCaml Higher Order Functions

CMSC 330: Organization of Programming Languages. OCaml Higher Order Functions

CMSC 631. Functional Programming with OCaml

CMSC 330: Organization of Programming Languages. Functional Programming with Lists

CMSC 330: Organization of Programming Languages. Functional Programming with Lists

CMSC 330: Organization of Programming Languages. Lets, Tuples, Records

CMSC 330: Organization of Programming Languages. Closures (Implementing Higher Order Functions)

COMP 150-AVS Fall OCaml and Functional Programming

CMSC 330: Organization of Programming Languages. Closures (Implementing Higher Order Functions)

Dialects of ML. CMSC 330: Organization of Programming Languages. Dialects of ML (cont.) Features of ML. Functional Languages. Features of ML (cont.

OCaml. ML Flow. Complex types: Lists. Complex types: Lists. The PL for the discerning hacker. All elements must have same type.

News. Programming Languages. Complex types: Lists. Recap: ML s Holy Trinity. CSE 130: Spring 2012

CMSC 330, Fall 2013, Practice Problem 3 Solutions

Programming Languages

CMSC 330, Fall 2013, Practice Problems 3

Programming Languages

Tail Calls. CMSC 330: Organization of Programming Languages. Tail Recursion. Tail Recursion (cont d) Names and Binding. Tail Recursion (cont d)

Programming Languages

CMSC 330: Organization of Programming Languages. Operational Semantics

CS Lectures 2-3. Introduction to OCaml. Polyvios Pratikakis

CMSC 330: Organization of Programming Languages. OCaml Expressions and Functions

# true;; - : bool = true. # false;; - : bool = false 9/10/ // = {s (5, "hi", 3.2), c 4, a 1, b 5} 9/10/2017 4

Plan (next 4 weeks) 1. Fast forward. 2. Rewind. 3. Slow motion. Rapid introduction to what s in OCaml. Go over the pieces individually

CS 321 Programming Languages

OCaml. History, Variants. ML s holy trinity. Interacting with ML. Base type: Integers. Base type: Strings. *Notes from Sorin Lerner at UCSD*

CMSC330. Objects, Functional Programming, and lambda calculus

Thinking Induc,vely. COS 326 David Walker Princeton University

So what does studying PL buy me?

Booleans (aka Truth Values) Programming Languages and Compilers (CS 421) Booleans and Short-Circuit Evaluation. Tuples as Values.

Haskell Types, Classes, and Functions, Currying, and Polymorphism

CSE341: Programming Languages Lecture 9 Function-Closure Idioms. Dan Grossman Winter 2013

Programming Languages. Tail Recursion. CSE 130: Winter Lecture 8: NOT TR. last thing function does is a recursive call

CMSC 330: Organization of Programming Languages

Haske k ll An introduction to Functional functional programming using Haskell Purely Lazy Example: QuickSort in Java Example: QuickSort in Haskell

A Second Look At ML. Chapter Seven Modern Programming Languages, 2nd ed. 1

CSE341: Programming Languages Lecture 9 Function-Closure Idioms. Dan Grossman Fall 2011

Lab 10: OCaml sequences, comparators, stable sorting 12:00 PM, Nov 12, 2017

OCaml Data CMSC 330: Organization of Programming Languages. User Defined Types. Variation: Shapes in Java

CSCI-GA Scripting Languages

CMSC 330: Organization of Programming Languages

An introduction introduction to functional functional programming programming using usin Haskell

Lecture 19: Functions, Types and Data Structures in Haskell

List Functions, and Higher-Order Functions

CMSC330 Fall 2016 Midterm #1 2:00pm/3:30pm

CS Lecture 6: Map and Fold. Prof. Clarkson Spring Today s music: Selections from the soundtrack to 2001: A Space Odyssey

CSc 372 Comparative Programming Languages

Any questions. Say hello to OCaml. Say hello to OCaml. Why readability matters. History, Variants. Plan (next 4 weeks)

CS Lecture 6: Map and Fold. Prof. Clarkson Fall Today s music: Selections from the soundtrack to 2001: A Space Odyssey

OCaml Language Choices CMSC 330: Organization of Programming Languages

The Haskell HOP: Higher-order Programming

CSc 372. Comparative Programming Languages. 8 : Haskell Function Examples. Department of Computer Science University of Arizona

Begin at the beginning

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

CS 11 Haskell track: lecture 1

CMSC330 Fall 2014 Midterm 2 Solutions

Lecture #23: Conversion and Type Inference

CMSC 330: Organization of Programming Languages. OCaml Imperative Programming

Conversion vs. Subtyping. Lecture #23: Conversion and Type Inference. Integer Conversions. Conversions: Implicit vs. Explicit. Object x = "Hello";

PROGRAMMING IN HASKELL. CS Chapter 6 - Recursive Functions

Informatics 1 Functional Programming Lecture 7. Map, filter, fold. Don Sannella University of Edinburgh

Shell CSCE 314 TAMU. Haskell Functions

Haskell Introduction Lists Other Structures Data Structures. Haskell Introduction. Mark Snyder

CMSC 330: Organization of Programming Languages. OCaml Data Types

CSE 130 [Winter 2014] Programming Languages

CMSC 330: Organization of Programming Languages. OCaml Imperative Programming

CMSC 330: Organization of Programming Languages. Rust Basics

Programming Languages

A Func'onal Introduc'on. COS 326 David Walker Princeton University

Functional Programming. Pure Functional Programming

CMSC330 Spring 2014 Midterm 2 Solutions

Topics Covered Thus Far. CMSC 330: Organization of Programming Languages. Language Features Covered Thus Far. Programming Languages Revisited

CS Lecture 5: Pattern Matching. Prof. Clarkson Fall Today s music: Puff, the Magic Dragon by Peter, Paul & Mary

COSE212: Programming Languages. Lecture 3 Functional Programming in OCaml

CMSC 330: Organization of Programming Languages. Objects and Functional Programming

Topics Covered Thus Far CMSC 330: Organization of Programming Languages

CMSC 330: Organization of Programming Languages. Formal Semantics of a Prog. Lang. Specifying Syntax, Semantics

Introduction to OCaml

Recap. Recap. If-then-else expressions. If-then-else expressions. If-then-else expressions. If-then-else expressions

PROGRAMMING IN HASKELL. Chapter 2 - First Steps

Haskell An Introduction

Some Advanced ML Features

CSE 130 Programming Languages. Lecture 3: Datatypes. Ranjit Jhala UC San Diego

Recap: Functions as first-class values

Functional abstraction. What is abstraction? Eating apples. Readings: HtDP, sections Language level: Intermediate Student With Lambda

Functional abstraction

CSci 4223 Principles of Programming Languages

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

Programming Language Concepts: Lecture 14

CSE 341 Section 5. Winter 2018

Which of the following expressions has the type int list?

To figure this out we need a more precise understanding of how ML works

CSE 341 : Programming Languages Midterm, Spring 2015

Today s Plan. Programming Languages. Example : Factorial. Recursion. CSE 130 : Spring Lecture 6: Higher-Order Functions

Week 5 Tutorial Structural Induction

According to Larry Wall (designer of PERL): a language by geniuses! for geniuses. Lecture 7: Haskell. Haskell 98. Haskell (cont) - Type-safe!

FUNCTIONAL PROGRAMMING

COSE212: Programming Languages. Lecture 4 Recursive and Higher-Order Programming

Transcription:

CMSC 330: Organization of Programming Languages OCaml 2 Higher Order Functions Tuples Constructed using (e1,..., en) Deconstructed using pattern matching Patterns involve parens and commas, e.g., (p1,p2, ) Tuples are like C structs But without field labels Allocated on the heap Tuples can be heterogenous Unlike lists, which must be homogenous (1, ["string1"; "string2"]) is a valid tuple 1 2 Examples With Tuples let plusthree (x, y, z) = x + y + z let addone (x, y, z) = (x+1, y+1, z+1) plusthree (addone (3, 4, 5)) (* returns 15 *) let sum ((a, b), c) = (a+c, b+c) sum ((1, 2), 3) = (4, 5) let plusfirsttwo (x::y::_, a) = (x + a, y + a) plusfirsttwo ([1; 2; 3], 4) = (5, 6) let tls (_::xs, _::ys) = (xs, ys) tls ([1; 2; 3], [4; 5; 6; 7]) = ([2; 3], [5; 6; 7]) Another Example let f l = match l with x::(_::y) -> (x,y) What is f [1;2;3;4]? Possibilities: ([1],[3]) (1,3) (1,[3]) (1,4) (1,[3;4]) Remember, semicolon for lists, comma for tuples [1, 2] = [(1, 2)] = a list of size one (1; 2) = Warning: This expression should have type unit 3 4 1

List And Tuple Types Tuple types use * to separate components List And Tuple Types Tuple types use * to separate components Examples (1, 2) : (1, "string", 3.5) : (1, ["a"; "b"], 'c') : [(1,2)] : [(1, 2); (3, 4)] : [(1,2); (1,2,3)] : Examples (1, 2) : int * int (1, "string", 3.5) : int * string * float (1, ["a"; "b"], 'c') : int * string list * char [(1,2)] : (int * int) list [(1, 2); (3, 4)] : (int * int) list [(1,2); (1,2,3)] : error Ø Because the first list element has type int * int, but the second has type int * int * int list elements must all be of the same type 5 6 Polymorphic Types Some functions we saw require specific list types let plusfirsttwo (x::y::_, a) = (x + a, y + a) plusfirsttwo : int list * int -> (int * int) But other functions work for any list let hd (h::_) = h hd [1; 2; 3] (* returns 1 *) hd ["a"; "b"; "c"] (* returns "a" *) OCaml gives such functions polymorphic types hd : 'a list -> 'a this says the function takes a list of any element type 'a, and returns something of that type Examples Of Polymorphic Types let tl (_::t) = t tl : 'a list -> 'a list let swap (x, y) = (y, x) swap : 'a * 'b -> 'b * 'a let tls (_::xs, _::ys) = (xs, ys) tls : 'a list * 'b list -> 'a list * 'b list let eq (x,y) = x = y eq : 'a * a -> bool 7 8 2

Tuples Are A Fixed Size This OCaml definition # let foo x = match x with (a, b) -> a + b (a, b, c) -> a + b + c;; Would yield this error message This pattern matches values of type 'a * 'b * 'c but is here used to match values of type 'd * 'e Tuples of different size have different types Thus never more than one match case with tuples 9 Conditionals Use if...then...else like C/Java/Ruby But no parentheses, no elsif, and no end if grade >= 90 then print_string "You got an A" else if grade >= 80 then print_string "You got a B" else if grade >= 70 then print_string "You got a C" else print_string "You re not doing so well" 10 Conditionals (cont.) In OCaml, conditionals return a result The value of whichever branch is true/false Like? : in C, C++, and Java # if 7 > 42 then "hello" else goodbye";; - : string = "goodbye" # let x = if true then 3 else 4;; x : int = 3 # if false then 3 else 3.0;; This expression has type float but is here used with type int The Factorial Function Using conditionals & functions Can you write fact, the factorial function? let rec fact n = if n = 0 then 1 else n * fact (n-1);; Notice no return statements This is pretty much how it needs to be written 11 12 3

Let Rec The rec part means define a recursive function Let vs. let rec let x = e1 in e2 x in scope within e2 let rec x = e1 in e2 x in scope within e2 and e1 Why use let rec? If you used let instead of let rec to define fact let fact n = if n = 0 then 1 else n * fact (n-1) in e2 Fact is not bound here! 13 Let More Examples let f n = 10;;;; let f n = if n = 0 then 1 else n * f (n 1);;;; f 0;;;; f 1;;;; (* 1 *) (* 10 *) let f x = f in f (* Unbound value f *) let rec f x = f in f (* Bound value f *) 14 Recursion = Looping Recursion is essentially the only way to iterate (The only way we re going to talk about) Another example let rec print_up_to (n, m) = print_int n; print_string "\n"; if n < m then print_up_to (n + 1, m) Lists and Recursion Lists have a recursive structure And so most functions over lists will be recursive let rec length l = match l with [] -> 0 (_::t) -> 1 + (length t) This is just like an inductive definition Ø The length of the empty list is zero Ø The length of a nonempty list is 1 plus the length of the tail Type of length? 15 16 4

More Examples More Examples (cont.) sum l (* sum of elts in l *) let rec sum l = match l with [] -> 0 (x::xs) -> x + (sum xs) negate l (* negate elements in list *) let rec negate l = match l with (x::xs) -> (-x) :: (negate xs) (* return a list containing all the elements in the list l followed by all the elements in list m *) append (l, m) let rec append (l, m) = match l with [] -> m (x::xs) -> x::(append (xs, m)) rev l (* reverse list; hint: use append *) let rec rev l = match l with (x::xs) -> append ((rev xs), [x]) last l (* last element of l *) let rec last l = match l with [x] -> x rev takes O(n 2 ) time. Can you do better? (x::xs) -> last xs 17 18 A Clever Version of Reverse let rec rev_helper (l, a) = match l with [] -> a (x::xs) -> rev_helper (xs, (x::a)) let rev l = rev_helper (l, []) Let s give it a try rev [1; 2; 3] rev_helper ([1;2;3], []) rev_helper ([2;3], [1]) rev_helper ([3], [2;1]) rev_helper ([], [3;2;1]) [3;2;1] More Examples flattenpairs l (* ('a * 'a) list -> 'a list *) let rec flattenpairs l = match l with ((a, b)::t) -> a :: b :: (flattenpairs t) take (n, l) (* return first n elts of l *) let rec take (n, l) = if n = 0 then [] else match l with (x::xs) -> x :: (take (n-1, xs)) 19 20 5

Working With Lists Several of these examples have the same flavor Walk through the list and do something to every element Walk through the list and keep track of something Recall the following example code from Ruby: Here we passed a code block into the collect method Wouldn t it be nice to do the same in OCaml? a = [1,2,3,4,5] b = a.collect { x -x } 21 Anonymous Functions Recall code blocks in Ruby Here, we can think of { x print x } as a function We can do this (and more) in Ocaml where (1..10).each { x print x } range_each (1,10) (fun x -> print_int x) let rec range_each (i,j) f = if i > j then () else let _ = f i in (* ignore result *) range_each (i+1,j) f 22 Anonymous Functions Passing functions around is very common So often we don t want to bother to give them names Use fun to make a function with no name Parameter (fun x -> x + 3) 5 fun x -> x + 3 Body = 8 All Functions Are Anonymous Functions are first-class, so you can bind them to other names as you like let f x = x + 3 let g = f g 5 In fact, let for functions is just shorthand let f x = body = 8 stands for let f = fun x -> body 23 24 6

Examples Higher-Order Functions let next x = x + 1 Short for let next = fun x -> x + 1 let plus (x, y) = x + y Short for let plus = fun (x, y) -> x + y Which is short for Ø let plus = fun z -> (match z with (x, y) -> x + y) let rec fact n = if n = 0 then 1 else n * fact (n-1) Short for let rec fact = fun n -> (if n = 0 then 1 else n * fact (n-1)) In OCaml you can pass functions as arguments, and return functions as results let plus_three x = x + 3 let twice f z = f (f z) twice plus_three 5 twice : ('a->'a) -> 'a -> 'a let plus_four x = x + 4 let pick_fn n = if n > 0 then plus_three else plus_four (pick_fn 5) 0 pick_fn : int -> (int->int) 25 26 Currying Curried Functions In OCaml We just saw a way for a function to take multiple arguments The function consumes one argument at a time, returning a function that takes the rest This is called currying the function Named after the logician Haskell B. Curry But Schönfinkel and Frege discovered it Ø So it should probably be called Schönfinkelizing or Fregging OCaml has a really simple syntax for currying let add x y = x + y This is identical to all of the following: let add = (fun x -> (fun y -> x + y)) let add = (fun x y -> x + y) let add x = (fun y -> x+y) Thus: add has type int -> (int -> int) add 3 has type int -> int Ø add 3 is a function that adds 3 to its argument (add 3) 4 = 7 This works for any number of arguments 27 28 7

Curried Functions In OCaml (cont.) Because currying is so common, OCaml uses the following conventions: -> associates to the right Ø Thus int -> int -> int is the same as Ø int -> (int -> int) function application associates to the left Ø Thus add 3 4 is the same as Ø (add 3) 4 Mental Shorthand You can think of curried types as defining multiargument functions Type int -> float -> float is a function that takes an int and a float and returns a float Type int -> int -> int -> int is a function that takes three ints and returns an int The bonus is that you can partially apply the function to some of its arguments And apply that to the rest of the arguments later 29 30 Another Example Of Currying A curried add function with three arguments: The same as Then... let add_th x y z = x + y + z let add_th x = (fun y -> (fun z -> x+y+z)) add_th has type int -> (int -> (int -> int)) add_th 4 has type int -> (int -> int) add_th 4 5 has type int -> int add_th 4 5 6 is 15 Implementing this is Challenging! Implementing functions that return other functions requires a clever data structure called a closure We ll see how these are implemented later In the meantime, we will explore using higher order functions, and then discuss how they are implemented 31 32 8

The Map Function Let s write the map function (like Ruby's collect) Takes a function and a list, applies the function to each element of the list, and returns a list of the results let rec map f l = match l with (h::t) -> (f h)::(map f t) let add_one x = x + 1 let negate x = -x map add_one [1; 2; 3] map negate [9; -5; 0] Type of map? The Map Function (cont.) What is the type of the map function? let rec map f l = match l with (h::t) -> (f h)::(map f t) ('a -> 'b) -> 'a list -> 'b list f l 33 34 Pattern Matching With Fun match can be used within fun map (fun l -> match l with (h::_) -> h) [ [1; 2; 3]; [4; 5; 6; 7]; [8; 9] ] = [1; 4; 8] But use named functions for complicated matches May use standard pattern matching abbreviations map (fun (x, y) -> x+y) [(1,2); (3,4)] = [3; 7] 35 The Fold Function Common pattern Iterate through list and apply function to each element, keeping track of partial results computed so far let rec fold f a l = match l with [] -> a (h::t) -> fold f (f a h) t a = accumulator Usually called fold left to remind us that f takes the accumulator as its first argument What's the type of fold? = ('a -> 'b -> 'a) -> 'a -> 'b list -> 'a 36 9

Example Another Example let rec fold f a l = match l with [] -> a (h::t) -> fold f (f a h) t let rec fold f a l = match l with [] -> a (h::t) -> fold f (f a h) t let add a x = a + x fold add 0 [1; 2; 3; 4] fold add 1 [2; 3; 4] fold add 3 [3; 4] fold add 6 [4] fold add 10 [] 10 let next a _ = a + 1 fold next 0 [2; 3; 4; 5] fold next 1 [3; 4; 5] fold next 2 [4; 5] fold next 3 [5] fold next 4 [] 4 We just built the sum function! We just built the length function! 37 38 Using Fold to Build Reverse let rec fold f a l = match l with [] -> a (h::t) -> fold f (f a h) t Can you build the reverse function with fold? let prepend a x = x::a fold prepend [] [1; 2; 3; 4] fold prepend [1] [2; 3; 4] fold prepend [2; 1] [3; 4] fold prepend [3; 2; 1] [4] fold prepend [4; 3; 2; 1] [] [4; 3; 2; 1] 39 10