an introduction to f# bogdan brinzarea-iamandi banca romaneasca 22 february 2010

56
Let the |> fun begin An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Upload: evan-logan

Post on 28-Dec-2015

217 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Let the |> fun beginAn introduction to F#

Bogdan Brinzarea-IamandiBanca Romaneasca

22 February 2010

Page 2: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Agenda

Topic Covered Today

History

From imperative to functional

Fundamentals

Data structures

Pattern matching

Immutability vs. Mutability

Object Oriented Programming

Async and Parallel Programming

25 February 2010

Unit testing 25 February 2010

Page 3: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

History

Page 4: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

F is for fun“The most original new face in computer languages since Bjarne Stroustrup developed C++ in the early 1980‘s”

http://www.simple-talk.com/opinion/geek-of-the-week/don-syme-geek-of-the-week/

Page 5: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

What is F#?

Functional Programming Language Will ship with Visual Studio 2010 Deep roots in OCaml (http://caml.inria.fr) Developed by Microsoft Research

http://research.microsoft.com/en-us/um/cambridge/projects/fsharp/

Page 6: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Why should F# matter to me?

Succinctness Type safety Type inference Expressivity Scripting Performance Seamless integration with .NET

Page 7: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Why should F# matter to me?

Functional programming Imperative programming Object oriented programming Scripted programming

Page 8: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Why should F# matter to me?

Well suited for: Technical programming Algorithmic programming Parallel programming Asynchronous programming Explorative programming Financial computing

Page 9: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

From imperative to functional programming

Page 10: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Fibonacci C#

static IEnumerable<int> Fibonacci{

get{ int i = 1; int j = 2; while (true) { int n = i; yield return n; i = j; j = j + n; }}

}

Page 11: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Fibonacci F#

let fibs = Seq.unfold (fun (i,j) -> Some(i,(j,i+j))) (1,2)

Page 12: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Functional programming

Much more like our mind thinks Easy to grasp for scientists Pure functional programming has no

side effects - immutability Highly parallelizable Powerful function support with

currying and composition

Page 13: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Functional features in other languages

C# 3.0 already has lambda expressions, anonymous functions, first class functions, anonymous types

Matthew Podwysocki - Functional C# http://code.msdn.microsoft.com/FunctionalCSharp/

Bart de Smethttp://bartdesmet.net/blogs/bart/

Luca Bolognesehttp://blogs.msdn.com/lucabol/

Page 14: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Imperative programming

Variable and assignment as main operations

In C# value types are immutable F# is not pure functional as it has

Flow control (for, while, if) Mutable keyword Reference cells Arrays

Page 15: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Imperative vs Functional

Characteristic Imperative Functional

Programmer focus How to perform tasks (algorithms) and how to track changes in state.

What information is desired and what transformations are required.

State changes Important. Non-existent.

Order of execution Important. Low importance.

Primary flow control Loops, conditionals, and function (method) calls.

Function calls, including recursion.

Primary manipulation unit

Instances of structures or classes.

Functions as first-class objects and data collections.

MSDN Library http://msdn.microsoft.com/en-us/library/bb669144.aspx

Page 16: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Fundamentals

Page 17: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

#light

Lightweight syntax Makes whitespaces significant Lets you leave out tokens such as begin end ; ;; in

Makes code more readable and concise

Page 18: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Hello world!

printfn "Hello world!"

Page 19: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Let keyword

// define a valuelet message ="Hello world!“

// define a function valuelet sqr x = x*x

Binds forever a value or function value to an identifier

DOES NOT assign a value to an identifier The identifiers are immutable The compiler infers the types

Page 20: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Type inference

F# is statically typed The compiler infers the type for all

variables and functions We need to specify only when it

cannot be deduced Every value and expression has a

definite type at compile time

Page 21: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Type inference

Automatic generalization - if the type is not specified it is inferred as generic

// 'a -> 'b -> 'a * 'blet pair x y = (x , y)

Page 22: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Type inference

The return type of a function is determined by the type of the last expression in the function.// int->int->intlet add1 x y = x + y + 1

// float->float->floatlet add10 x y = x + y + 1.0

Page 23: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Type inference

We can give the compiler a little help

// help inferring the type let (message:string) = "Hello world!"

let add (x:float) (y:float) = x+y let sum = add 2.0 1.0

Page 24: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Fun or lambda expressions

Can be used as parameters to other functions

let squares = Array.map (fun x->x*x) [|0..10|]

Page 25: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Recursive functions

Functions are not recursive by default

Make sure the recursively function ends

Use the rec keyword together with let

let rec Fibonacci n = if n<2 then n else Fibonacci n-1 + Fibonacci n-2

Page 26: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Currying or partial functions

Named after Haskell Curry A function that calls another function

and returns a function or A partial function

let add x y = x + y let add5 = add 5 let result = add5 6

Page 27: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Local identifiers

Indentation matters

let SquareAndSum x y = let sqr x = x * x sqr x + sqr y

Page 28: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Basic operators

Arithmetic operators Description

x + y Addition

x – y Subtraction

x * y Multiplication

x / y Division

x % y Modulus

x ** y Power of

Boolean operator Description

not Boolean NOT

|| Boolean OR

&& Boolean AND

Page 29: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Basic types

F# type C# type Examplebool Boolean truebyte Byte 45ysbyte SByte 45uyint16 Int16 45suint16 UInt16 45usint Int32 45uint UInt32 45uint64 Int64 45Luint64 UInt64 45ULchar Char ‘c’decimal Decimal 45Mstring String “A string”unit not applicable ()

Page 30: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Pipelines and functions composition

Scientists love it Composition f(g(x)) g >> f

Pipelines take an input of a function and pass it to the next oneinput |> function 1 |> function 2

Page 31: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Data types

Page 32: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Tuples

A group of unnamed but ordered values

Can contain different types In .NET System.Tuple

Page 33: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Arrays

All elements of the array must have the same type

Elements are mutable A lot of helper functions to choose from

(map, filter, iter etc.) let array1 = [| 0; 1; 2 |]

let array2 = [| 0..10 |]

let array3 = [| for i in 0..10 -> i |]

Page 34: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Lists

A series of elements all of same (base) type

Lists are immutable :: (cons operator) adds an element

to the head of the list @ concatenates lists Head, Tail properties A lot of helper functions to choose

from (head, tail, nth, map, iter, filter) let list1 = [ 1;2;3]

Page 35: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Sequences

A series of elements all of same type Equivalent to System.Collections.Generic.IEnumerable

Sequence expressions evaluate to sequences

A lot of helper functions to choose from (map, filter, iter) same as for lists

let seq1 = seq {1..10}

Page 36: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Discriminated unions

A way of grouping different values and types

Used to represent tree structures Data is not fixed Each possible option has a case

identifier

type Tree = | Nil | Node of int * Tree * Tree

Page 37: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Options

An option wraps a value indicating whether it exists or not

They are a simple example of discriminated union// a: int option let a = Some (42)// b: 'a optionlet b = None

Page 38: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Records

Simple way of grouping named values

We can use record expressions to set values

Easy cloning with copy and update record expressions

Page 39: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Pattern matching

Page 40: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Pattern matching at a glance

Offers branching of the control based on comparison of an expression with a set of patterns

One of the most powerful features of F#

Not a simple switch statement Haskell, ML and OCaml also have it

Page 41: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

match expressions

When guards to add extra condition to the pattern

// Match expressionmatch test-expression with | pattern1 [ when condition ] -> result-expression1

| pattern2 [ when condition ] -> result-expression2

| ...

Page 42: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Patterns

Name ExampleConstant pattern 1.0,"test",30,Color.Red

Identifier pattern Some(x)Failure(msg)

Variable pattern A

as pattern (a, b) as tuple1

OR pattern ([h] | [h; _])

AND pattern (a, b) & (_, "test")

Cons pattern h :: t

List pattern [ a; b; c ]

Array pattern [| a; b; c |]

Page 43: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Patterns

Name ExampleParenthesized pattern ( a )

Tuple pattern ( a, b )

Record pattern { Name = name; }

Wildcard pattern _

Pattern together with type annotation

a : int

Type test pattern :? System.DateTime as dt

Null pattern null

Page 44: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Pattern matching

let rec f = function | x when x < 0 -> failwith "Negative values are not allowed."

| 0 | 1 as x -> x | x -> f (x-1) + f (x-2)

Page 45: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Active patterns

Pattern matching of Algebraic Data Types (ADTs)

Allow to define named partitions for input data

Partial active patterns when we need to partition only part of the input

Parameterized active patterns when we have more than one argument

Page 46: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Mutability vs immutability

Page 47: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Mutability

Use mutable to make a variable mutablelet mutable a = 1a <- 2

Arrays are mutablelet array = [|1..10|]array.[2] <- 5

Page 48: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Reference cells

ref operator allows to box mutable values inside reference cellstype Ref<'a> =

{ mutable contents: 'a } byref keyword to ask for a reference

cell or the address of a typical variable

Page 49: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Object Oriented Programming

Page 50: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Classes

type [access-modifier] type-name [type-params]( parameter-list ) [ as identifier ] =

[ class ] [inherit base-type-name(base-constructor-args) ]

[ let-bindings ] [ do-bindings ] member-list Let bindings define fields or function values

local to the class Do bindings define code to be executed upon

creation Identifier gives a name to the instance variable

Page 51: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Classes

new(argument-list) = constructor-body

new allows to define other constructors

Page 52: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Interfaces

// Interface declarationtype interface-name = [ interface ] abstract member1 : [ argument-types1 -> ] return-type1 abstract member2 : [ argument-types2 -> ] return-type2 ... // Implementing, inside a class type definition: interface interface-name with

member self-identifier.member1 argument-list = method-body1 member self-identifier.member2 argument-list = method-body2

// Implementing, by using an object expression let class-name (argument-list) = {

new interface-name with member self-identifier.member1 argument-list = method-body1 member self-identifier.member2 argument-list = method-body2 [ base-interface-definitions ]

} member-list

Page 53: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Abstract classes

// Abstract class syntax.type [ accessibility-modifier ] abstract-class-name

= [ inherit base-class-or-interface-name ] [ abstract-member-declarations-and-member-

definitions ]

// Abstract member syntax. abstract member member-name : type-signature

Page 54: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Inheritance

Virtual methods abstract member method-name : typedefault self-identifier.method-name argument-

list = method-bodyoverride self-identifier.method-name argument-

list = method-body

Use object expressions as an alternative

Page 55: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Generics

Values, methods, properties, classes, records, discriminated unions

Implicit generic constraint via type inference

Explicit generic constraint

Page 56: An introduction to F# Bogdan Brinzarea-Iamandi Banca Romaneasca 22 February 2010

Resources

Expert F# by Don Syme Programming F# by Chris Smith CTO Corner - http://ctocorner.com/fsharp/book/ HubFS

http://cs.hubfs.net/ Matthew Podwysocki

http://weblogs.asp.net/podwysocki/ Don Syme

http://blogs.msdn.com/dsyme Chris Smith

http://blogs.msdn.com/chrsmith/