Continuing on with my journey in F# tonight I went through the next section in tryfsharp.org called “The Functional World”. Like usual here are some random notes on the section.
-
If you want to define what the return type should be in an F# function use a : and the return type.
This is usually a good practice to over annotate the code to allow for a better form of self documenting code so the reader does not need to infer what actual parameter types and return types.let sqr (x : float) : float = x * x
-
if-then-else statements in F# are actually called if expressions where the expression will evaluate to either true or false.
let printYes (x : float) : string = if x >= 10.0 then "yes" else "no" let good = printYes(10.0) -
If you need to create a recursive function you need to add the keyword “rec” in front of the function definition. This allows for added safety so you do not accidentally create a recursive function. This keyword will also allow for the function to be accessible internally to the function.
let rec factorial (n : int) = if n = 0 then 1 else n * factorial (n-1) -
You can guard against infinite recursion in a function by defining an assert which stops the function from creating a stack overflow exception.
Instead of calling the assert you could throw an exception if the parameters are outside of bounds.let rec power (x : float) (n : int) = assert (n >= 0) if n = 0 then 1.0 else x * power x (n-1)let rec power (x : float) (n : int) = if n - Arrays are not part of the functional programming paradigm (but they can be used). Instead lists are commonly used instead.
- Lists are very efficient at adding to the front from a list and creating and conversely at removing an item from the front of a list.
-
You can retrive the head of a list by calling List.head list
To obtain the tail you can use List.taillet list = ['h';'e';'l'; 'l'; 'o'] let head = List.head list
let list = ['h';'e';'l'; 'l'; 'o'] let tail = List.tail list
-
The F# list library contains additional helper functions to work with list for example you can use List.exists to see if a given list contains a given element.
let found = List.exists (fun element -> element = 'l') list
-
You can use pattern matching on list to help find elements in a list.
Here the :: operator helps to decompose the list to the head element and rest which contains the tail element and the other elements.let rec contains list element = match list with | [] -> false | head :: rest -> if head = element then true else contains rest element let foundByContains = contains list 'h' -
Functions which accept functional arguments and or return new functions are known as higher order functions. Some examples of these functions are:
- List.map - which executes a function on each element in a list.
- List.filter - filters a list of elements which match the given function predicate
- List.reduce - applies the a given function to the first two elements that result is than passed to the third element and that result is applied to the fourth and so on.
- List.fold - applies a function to each element in a list but also passes along a variable along which is called the accumulator.
Example was from msdn with revised names to make sense.let data = [("Cats",4); ("Dogs",5); ("Mice",3); ("Elephants",2)] let count = List.fold (fun accumulator (animalType, numberOfAnimals) -> accumulator + numberOfAnimals) 0 data printfn "Total number of animals: %d" count
So far F# is looking good, I am slowly starting to understand the syntax. The lack of () {} is the hardest part for me to grasp. Next up on the list is the “Imperative World”