Feb 7, 2015 Thinking in Clojure. Jumping in We’ll quickly go through Clojure’s data types, some basic functions, and basic syntax Then we’ll get to the.

Slides:



Advertisements
Similar presentations
Lisp. Versions of LISP Lisp is an old language with many variants Lisp is alive and well today Most modern versions are based on Common Lisp LispWorks.
Advertisements

1 Programming Languages (CS 550) Lecture Summary Functional Programming and Operational Semantics for Scheme Jeremy R. Johnson.
Functional Programming. Pure Functional Programming Computation is largely performed by applying functions to values. The value of an expression depends.
Lambda Calculus and Lisp PZ03J. Lambda Calculus The lambda calculus is a model for functional programming like Turing machines are models for imperative.
Chapter 3 Functional Programming. Outline Introduction to functional programming Scheme: an untyped functional programming language.
CS 355 – PROGRAMMING LANGUAGES Dr. X. Apply-to-all A functional form that takes a single function as a parameter and yields a list of values obtained.
Clojure Template Tail Recursion. Hello, Factorial! The factorial function is everybody’s introduction to recursion (defn factorial-1 [n] (if (zero? n)
16-May-15 Sudden Python Drinking from the Fire Hose.
Lists Introduction to Computing Science and Programming I.
Introduction to Computers and Programming Lecture 9: For Loops New York University.
Lisp. Versions of LISP Lisp is an old language with many variants –LISP is an acronym for List Processing language Lisp is alive and well today Most modern.
16-Jun-15 Recursion. 2 Definitions I A recursive definition is a definition in which the thing being defined occurs as part of its own definition Example:
The Scheme Programming Language History and Significance Dmitry Nesvizhsky CIS24 Professor Danny Kopec.
Introduction to Python
28-Jun-15 Recursion. 2 Definitions I A recursive definition is a definition in which the thing being defined occurs as part of its own definition Example:
Introducing the Erlang Language Why Erlang?  Exemplifies the “you can have code and concurrency that is free from side effects…there is no other way”
28-Jun-15 Recognizers. 2 Parsers and recognizers Given a grammar (say, in BNF) and a string, A recognizer will tell whether the string belongs to the.
29-Jun-15 Recursion. 2 Definitions I A recursive definition is a definition in which the thing being defined occurs as part of its own definition Example:
Recursion. Definitions I A recursive definition is a definition in which the thing being defined occurs as part of its own definition Example: A list.
Clojure 3 Recursion, Higher-order-functions 27-Aug-15.
Functional Programing Referencing material from Programming Language Pragmatics – Third Edition – by Michael L. Scott Andy Balaam (Youtube.com/user/ajbalaam)
ISBN Chapter 15 Functional Programming Languages.
Functional Programming in Scheme and Lisp. Overview In a functional programming language, functions are first class objects. You can create them, put.
Introduction to Scheme CS 480/680 – Comparative Languages “And now for something completely different…” – Monty Python “And now for something completely.
Functional Programming and Lisp. Overview In a functional programming language, functions are first class objects. In a functional programming language,
Solving N-Queens in Clojure
Clojure 4 Sequences 20-Oct-15. Clojure errors (NO_SOURCE_FILE:12) Useless--just means you’re running from the REPL shell java.lang.Exception: EOF while.
Collecting Things Together - Lists 1. We’ve seen that Python can store things in memory and retrieve, using names. Sometime we want to store a bunch of.
Clojure 2 Feb 7,
Data TypestMyn1 Data Types The type of a variable is not set by the programmer; rather, it is decided at runtime by PHP depending on the context in which.
Python Primer 1: Types and Operators © 2013 Goodrich, Tamassia, Goldwasser1Python Primer.
Clojure “Lisp Reloaded”. 2 Versions of LISP Lisp is an old language with many variants LISP is an acronym for List Processing language Lisp is alive and.
1 Printing in Python Every program needs to do some output This is usually to the screen (shell window) Later we’ll see graphics windows and external files.
1 FP Foundations, Scheme In Text: Chapter Chapter 14: FP Foundations, Scheme Mathematical Functions Def: A mathematical function is a mapping of.
Recursion. Definitions I A recursive definition is a definition in which the thing being defined occurs as part of its own definition Example: A list.
Quiz 3 Topics Functions – using and writing. Lists: –operators used with lists. –keywords used with lists. –BIF’s used with lists. –list methods. Loops.
Clojure Macros. Homoiconicity All versions of Lisp, including Clojure, are homoiconic This means that there is no difference between the form of the data.
Artificial Intelligence and Lisp Lecture 6 LiU Course TDDC65 Autumn Semester,
CS314 – Section 5 Recitation 9
Lets and Loops Tail Recursion.
Functional Programming
Clojure “Lisp Reloaded”.
Lists in Lisp and Scheme
Recursion 12-Nov-18.
Important Concepts from Clojure
Lesson 2: Building Blocks of Programming
Important Concepts from Clojure
Clojure “Lisp Reloaded”.
Thinking in Clojure 23-Nov-18.
Clojure 4 Sequences 27-Nov-18.
Recursion 2-Dec-18.
Recursion 2-Dec-18.
FP Foundations, Scheme In Text: Chapter 14.
Functions and Macros.
CISC101 Reminders Assn 3 due tomorrow, 7pm.
Clojure 4 Sequences 5-Dec-18.
Recursion 29-Dec-18.
Thinking in Clojure 1-Jan-19.
Thinking in Clojure 1-Jan-19.
Lisp and Scheme I.
Clojure “Lisp Reloaded”.
Clojure “Lisp Reloaded”.
Clojure Macros.
Recursion, Higher-order-functions
Important Concepts from Clojure
Recursion 23-Apr-19.
CISC101 Reminders Assignment 3 due today.
Clojure 3 1-Jun-19.
Thinking in Clojure 8-Jun-19.
Lisp.
Presentation transcript:

Feb 7, 2015 Thinking in Clojure

Jumping in We’ll quickly go through Clojure’s data types, some basic functions, and basic syntax Then we’ll get to the good stuff! 2

Clojure’s data types Clojure has: Lists, enclosed in parentheses and separated by spaces or commas: (a 17 "Plenty of parentheses") Functions: (fn [x] (first(rest x) ) Numbers: All Java numeric types, plus ratios and exact decimals: 5, 5.3, 5.3e30, 077, 0xFF00FF, 3/5, 5.3M Strings, as in Java: "She said \"Hello\"" Characters: \a, \5, \n, \newline, \tab, etc. The booleans true and false nil, equivalent to Java’s null Symbols, which stand for themselves: :meadow, :CIS-554 Vectors: [5 :a "hi!"] Maps: {:one 1, :two 2} Sets: #{:prolog :clojure} 3

Some basic Clojure functions Syntax of a function call: (function args ) Basic operations—sequences (seq) are lists, sets, maps, vectors: (quote arg ) or ' arg, to keep arg from being evaluated (first seq ) is the first element in the sequence (or nil ) (rest seq ) is what remains when the first element is removed (or nil ) (cons arg seq ) returns a new sequence with arg as its first element (= args ) tests whether its args are equal (empty? seq ), (list? seq ), ( seq? arg ), (nil? arg ) are more tests Basic arithmetic (+ args ), (- args ), (* args ), (/ args ), (< args ), etc. Basic logic (and args ), (or args ), (not arg ), (if condition result1 result2 ) Defining values ( def name value ) defines the name to be the given value ( defn name argv value ) is shorthand for (def name argv value ), where argv is a vector 4

Functions and special forms The arguments to a function are evaluated before the function is called Example: (* 2 (+ 3 4)) The function * is called with the arguments 2 and 7 A special form looks just like a function, but it gets its arguments unevaluated The special form itself decides when and whether to evaluate its arguments quote does not evaluate its argument if evaluates its first argument, then decides which of the second and third arguments to evaluate Clojure allows you to define your own special forms This means you can define your own control structures 5

A typical Clojure function (defn first-double-letter "Returns the first doubled letter in a string, or nil." [s] (if (< (count s) 2) nil (if (= (first s) (second s)) (first s) (first-double-letter (rest s)) ) ) ) user=> (first-double-letter "Pennsylvania") \n user=> (first-double-letter '( )) 5 6

It’s easier with cond cond is an if … then … else if … then … else … construct: (cond test1 result1 test2 result2 … testN resultN ) It requires an even number of parameters (one result for each test) The symbol :else may be used as the last test (defn first-double-letter "Returns the first doubled letter in a string, or nil." [s] (cond (< (count s) 2) nil (= (first s) (second s)) (first s) :else (first-double-letter (rest s)) ) ) user=> (first-double-letter "Pennsylvania") \n user=> (first-double-letter '( )) 5 7

It’s all about recursion Some rules of doing recursion: 1. Handle the base cases directly (without recursion) 2. Recur only with a simpler case 3. Don’t use global variables 4. Don’t “look down” into the recursion—that will just confuse you In Clojure you are almost always working with a list or some similar sequence Lisp programmers say, “Do something with the head, and recur with the tail” Clojure’s terms for “head” and “tail” are “first” and “rest” This pretty much covers rules 1 and 2 above Clojure doesn’t have global variables This covers rule #3 above Rule 4 always holds. Think about what you are doing now, not what some recursive call is doing 8

Functional programming Clojure is functional—what does that mean? Functions are like functions in math—called with the same arguments, they always return the same result This means: No “global variables,” no dependence on external values, and no side effects! Functions are values, or first-class objects Functions can be passed as parameters to functions, returned as the value of functions, created as needed, stored in data structures, and there are operations on functions that produce new functions The “blub paradox” applies—the value added is substantial, but not obvious to an imperative or object-oriented programmer Data is immutable (like strings in Java) Clojure’s data structures are designed to make this efficient Immutable data greatly simplifies concurrent programming Because data is immutable, loops are unnecessary (use recursion instead!) 9

Costs and benefits Costs of functional programming It’s weird and unfamiliar How can you do anything without objects, mutable variables, or loops? (Loops are used primarily to change the values of things) As a manager, functional programmers are hard to find (and expensive!) Clojure, and Lisp dialects generally, have too many parentheses! Benefits of functional programs Easier to write correct programs “Yeah, right!” – “No, really! All data is local and immutable.” Easier to write unit tests, because function values depend only on inputs Much easier to write concurrent programs Operations on collections make code simpler and more concise The simpler foundation means less syntax and fewer special cases Some operations, such as equality testing, are really fast But it’s still weird! 10

Easier to write correct programs Programs are easier to write when all data is local When relevant values can be changed elsewhere in the program—possibly in many places—it’s harder to see all the connections Functions in a functional language get all relevant input from the parameter list Unit testing is easier, because there are no dependencies on functions that may or may not have been called previously There is no need for a setUp method Functional programming supports powerful operations on sequences The imperative and object-oriented programming styles have been characterized as “word by word” programming Some sequence operations, such as membership testing, are provided for you In a functional language, any function can be a sequence operation 11

The problem of state Nonfunctional programming language are “stateful” or “have state” The state of a program is given by (1) the values of all the variables throughout the program, and (2) the current locus of execution That can be a huge amount of information to keep track of! Object-oriented programmers try to control complexity by having objects be responsible for their own state, and “loosely coupled” (not very dependent on) other objects Methods often have “side effects,” that is, they modify state Functional languages try to avoid having state at all This isn’t always easy Purely functional languages cannot have side effects Since I/O is a side effect, this is an even more difficult restriction 12

Maintaining state, functionally Sometimes you just need state Consider an adventure game You need to keep track of where you are, where other objects are, what you are holding, which paths are blocked or open, etc.—this is your state You do not need to keep track of permanent, immutable data; for example, most paths between rooms are fixed and unchanging—this isn’t part of the state In a functional program, a “state” is just an immutable (and usually just one) data item The data item can be quite complex, such as a dictionary States are immutable, but you can always create a “new” state that is a variation of a given state With carefully designed data structures, not as much storage is required as you might expect So the functional solution to maintaining state is: Pass one state into a function, get a new (and different) state back! 13

Clojure’s I/O compromise A purely functional program has no side effects I/O is a side effect Therefore: A purely functional program cannot do I/O! In Clojure, all functions return a value (print args ) and (println args ) return nil Clojure allows side effects in two well-defined places: (do args ) evaluates all its arguments in order, but returns only the value of the last one When a function (fn argv args ) is called, the arguments are evaluated in order, but only the last value is returned Example: (defn powers "Computes cube and square" [] (def n (read)) (println (* n n n)) (println (* n n)) n) 14

Lists are immutable 15 Here is a typical list: ABC my-list Here is (rest my-list) Here is (cons 'w my-list) w Notice that my-list remains unchanged Vectors, hash maps, sorted maps, hash sets, and sorted sets are similarly immutable

Functions are just values user=> (cons 'w '(a b c)) (w a b c) user=> (defn swap-args [f x y] (f y x)) #'user/swap-args user=> (swap-args cons '(a b c) 'w) (w a b c) user=> (defn apply-n-times [f x n] "Apply f to x, n times: f(f(f..(n)...))" (if (zero? n) x (apply-n-times f (f x) (dec n)) ) ) #'user/apply-n-times user=> (apply-n-times (fn [x] (* 2 x)) 1 10)

Collatz, the hard way Definition: collatz(1) = 1 collatz(n) = collatz(n / 2) if n is even collatz(n) = collatz(3 * n + 1) user=> (defn collatz [n] (let [ do-even (fn [n] (collatz (/ n 2))) do-odd (fn [n] (collatz (inc (* 3 n)))) ] (print n " ") (if (= n 1) 1 (if (even? n) (do-even n) (do-odd n)) ) ) ) #'user/collatz user=> (collatz 7)

map, filter, and reduce Here are three powerful functions you will find in almost any functional programming language map – apply a function to every element of a sequence, returning a sequence of results user=> (map even? '( )) (false false true false true) filter – apply a predicate to every element of a sequence, returning a sequence of those that satisfy the predicate user=> (filter even? '( )) (4 6) reduce – use a function to reduce a sequence to a single value user=> (reduce * '( )) 72 18

The real problem with state For decades we’ve been dealing with mutable state Mutable state + concurrency = nondeterminism We use threads and locks and semaphores and so on These are complicated, unsafe, and inefficient As Herb Sutter points out in The Free Lunch is Over, we have hit a 3 GHz barrier Since 2003, computers have not gotten faster We still want them faster Concurrency is the only solution Functional languages, with immutable state, provide a partial solution As Martin Odersky points out, you can hide from concurrency for a while yet…but not forever Important consequences: All newer languages are gaining functional and concurrent features Older languages, such as Java, are also trying to integrate these features “You can run, but you can’t hide!” 19

Oh, and by the way… Clojure has Infinite sequences Lazy sequences Exact decimal arithmetic Function composition Function currying Macros And lots more No version of Lisp has ever become mainstream They just get mugged in dark alleys and their ideas stolen! 20

The End 21