Category Archives: F#

F#30 : Type Providers

This is the final post on the initial proposed F# series that I had planned. That doesn’t mean there may not be more from me in the future but this will be the final one in the current batch. So what will this one be on?

This one will be on type providers. Type providers are a fairly complex beast, and they certainly do not fit into a beginners space (at least not in my opinion), so we will be concentrating on using Type Providers and not how to create them (standing on the shoulders of giants if you like).

So What Are Type Providers

Here is what MSDN has to say about type providers: http://msdn.microsoft.com/en-gb/library/hh156509.aspx

An F# type provider is a component that provides types, properties, and methods for use in your program. Type providers are a significant part of F# 3.0 support for information-rich programming. The key to information-rich programming is to eliminate barriers to working with diverse information sources found on the Internet and in modern enterprise environments. One significant barrier to including a source of information into a program is the need to represent that information as types, properties, and methods for use in a programming language environment. Writing these types manually is very time-consuming and difficult to maintain. A common alternative is to use a code generator which adds files to your project; however, the conventional types of code generation do not integrate well into exploratory modes of programming supported by F# because the generated code must be replaced each time a service reference is adjusted.

The types provided by F# type providers are usually based on external information sources. For example, an F# type provider for SQL will provide the types, properties, and methods you need to work directly with the tables of any SQL database you have access to. Similarly, a type provider for WSDL web services will provide the types, properties, and methods you need to work directly with any WSDL web service.

The set of types, properties, and methods provided by an F# type provider can depend on parameters given in program code. For example, a type provider can provide different types depending on a connection string or a service URL. In this way, the information space available by means of a connection string or URL is directly integrated into your program. A type provider can also ensure that groups of types are only expanded on demand; that is, they are expanded if the types are actually referenced by your program. This allows for the direct, on-demand integration of large-scale information spaces such as online data markets in a strongly typed way.

 

But I actually prefer what one user said on this StackOverflow post : http://stackoverflow.com/questions/4711537/f-type-providers-how-do-they-work

Say you have some arbitrary data entity out in the world. For this example, let’s say it’s a spreadsheet. Let’s also say you have some way to get/infer schema/metadata for that data – that is, you can know types (e.g. double versus string) and relationships (e.g. this column means ‘salary’) and metadata (e.g. this sheet is for the June 2009 budget).Type providers lets you code up a kind of ‘shim library’ that knows about some kind of data entity (e.g. a spreadsheet) and use that library as part of the compiler/IDE toolchain so that you can write code like

mySpreadsheet.ByRowAndColumn.C4

or something, and get Intellisense (autocompletion) and tooltips (e.g. describing cell C4 as Salary for Bob) and static typing (e.g. have it be a double or a string or whatever it is). Essentially this gives you the tooling affordances of statically-typed object models with the ease-of-use leverage of various dynamic or code-generation systems, with some improvements on both. The ‘cost’ is that someone has to write the shim library (the ‘type provider’), but many such providers are very general (e.g. one that speaks OData or Excel or WMI or whatnot) and so a small handful of type provider libraries makes vast quantities of the world’s data available in your programming language with static typing and first-class tooling support.

The architecture is an open compiler, where provider-authors implement a small interface that allows them to inject new names/types into the programming context.

 

What is clear is that type providers must be doing a whole lot of work behind the scenes to create new types, which must be using something like Reflection.Emit to create new types based on initial metadata, at the compilation stage, which is pretty whack.

 

Where Can I Get Me Some Type Providers

F# 3.0 comes with a few standard Type providers, namely the following ones that have sample usages shown at the links below, I however will not be covering these particular type providers, as they al rely on external things(such as SQL server) that are a bit hard for me to demo in a blog post, and I wanted to show examples in this F# series that would allow users to kind of copy and paste the code I have posted here. So If you want to try out the type providers listed below you will have to follow the links which will take you to the relevant examples.

 

We will be looking at some other type providers that have some more manageable dependencies, such as an Xml file, a CSV file etc etc

So where can you get your hands on these extra type providers? There is a F# data library which contains many type providers which you can read more about here : http://fsharp.github.io/FSharp.Data/, and it is also available as a NuGet package, so it is nice and easy to install. When you download this package you will get the following type providers:

  • JSON type provider
  • XML type provider
  • CSV type provider
  • Worldbank type provider
  • Freebase type provider

You may have a need for another type provider, someone may have even written one for you, so it is worth doing a quick google search before you set off to write your own one.

 

How Can I Use These Here Type Providers

As I say there will be a multitude of type providers out there in the wild, so chances are there may be one doing what you need. In this post I will be concentrating on 2 type providers found in the  F# data library that I just mentioned. I will not be covering all of the functions of these type providers, as the original authors have some great documentation on them anyway.

Xml Type Provider

Here is a simple example that shows how to use the type provider to parse some Xml.

open System
open FSharp.Data

//create a type provider to create the initia metadata
type Detailed = XmlProvider<"""<author><name full="true">Karl Popper</name></author>""">

[<EntryPoint>]
let main argv =

    //now parse using known metadata
    let info = Detailed.Parse("""<author><name full="false">Thomas Kuhn</name></author>""")
    printfn "%s (full=%b)" info.Name.Value info.Name.Full

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

Which when run gives this result:

image

 

The key points to take away from this are:

  • We get intellisense for this data that we do not actually have a concrete type for, it is simply inferred by the type provider
  • We can use the properties of the type that has been inferred

This is pretty crazy stuff when you stop and think about it

 

Here is slightly more advanced version of the xml type provider that shows how to deal with multiple nodes, and a separate xml file

open System
open FSharp.Data

//create a type provider to create the initia metadata
type Authors = XmlProvider<"C:\Users\sacha\Desktop\ConsoleApplication1\ConsoleApplication1\Writers.xml">

[<EntryPoint>]
let main argv =

    //now parse using known metadata
    let authors = """
      <authors topic="Philosophy of Mathematics">
        <author name="Bertrand Russell" />
        <author name="Ludwig Wittgenstein" born="1889" />
        <author name="Alfred North Whitehead" died="1947" />
      </authors> """

    let topic = Authors.Parse(authors)

    printfn "%s" topic.Topic
    for author in topic.Authors do
      printf " – %s" author.Name
      author.Born |> Option.iter (printf " (%d)")
      printfn ""

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

 

Which when run gives the following output

image

 

Csv Type Provider

Here is another example to a CSV file this time.

open System
open FSharp.Data

//create a type provider to create the initia metadata
type Stocks = CsvProvider<"C:\Users\sacha\Desktop\ConsoleApplication1\ConsoleApplication1\MSFT.csv">

[<EntryPoint>]
let main argv =

    //now parse using known metadata
    // Download the stock prices

    let data = "Date,Open,High,Low,Close,Volume,Adj Close
                2012-01-27,29.45,29.53,29.17,29.12,44187700,22.23
                2012-01-26,29.61,29.70,29.40,29.13,49102800,23.50
                2012-01-25,29.07,29.65,29.07,29.14,59231700,24.56
                2012-01-24,29.47,29.57,29.18,29.15,51703300,25.34"

    let msft = Stocks.Parse(data)

    // Look at the most recent row. Note the 'Date' property
    // is of type 'DateTime' and 'Open' has a type 'decimal'
    let firstRow = msft.Rows |> Seq.head
    let lastDate = firstRow.Date
    let lastOpen = firstRow.Open

    // Print the prices in the HLOC format
    for row in msft.Rows do
      printfn "HLOC: (%A, %A, %A, %A)" row.High row.Low row.Open row.Close

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

 

I also wanted to call out the fact that the data types are correct, where the following is true

  • Date is a DateTime
  • Open is decimal

This can be seen in the screen shot below, where I was hovering the mouse over the firstRow.Date expression here

image

 

I think type provider are pretty crazy, and do a lot of good work behind the scenes, I hope you too can see the value of them, and explore what is out there, and give them a try.

 

 

That’s It

Like I say this is the final post in this series, and my it’s been quite the ride for me, I just hope you guys/gals also enjoyed it. I would love to know actually, I got a bit of feedback along the way, but it would be nice to know if people have enjoyed this series, and whether it hit the mark or not. So if you feel inclined to leave me a comment, or want to buy me a virtual beer, I would love to hear about that. I also accept travellers cheques, free holidays and Lego for my kid. He likes fire engines.

Ha Ha.

Anyway thanks for listening to my rants on F#. I will now be getting back to my roots, which is writing articles for CodeProject which I really enjoy, so until we all meet again, adios, see you later. Happy F#ing

Advertisements

F#29 : Interop

In this post we will examine how F# can be used to do various tasks that you may have commonly use C#/VB.NET for. It will also show how to interop between F#/C# and vice versa. I have already shown some of the content here in previous posts, so apologies for that in advance.

Downloadable Code For This Post

As this post deals with a lot of different things, and concepts,  I took pity on you lot, and have uploaded a ZIP file that contains all the code for this post, which is available right here :

https://dl.dropboxusercontent.com/u/2600965/Blogposts/2014/WPFAppDemo.zip

Creating A Console App With F#

One of the things you may like to do with F# is create a console application. This is really simple as Visual Studio comes with a template for this, so it really is just a case of clicking a button. This can be seen in the screen shot below:

image

Using this Visual Studio template will give you this basic Console Application code:

[<EntryPoint>]
let main argv =
    printfn "%A" argv
    0 // return an integer exit code

In fact we covered a lot of ground explaining the inners of a F# console application in the very 1st post in this series: https://sachabarbs.wordpress.com/2014/02/25/f-1-hello-world/

Creating A Simple Windows Form App With F#

You may wish to create Windows Forms Applications in F#. There is no inbuilt template for this so you just need to make sure you

  1. reference the correct Dlls, which for most Windows Forms applications would simply be “System.WIndows.Forms”
  2. Change the project type to a Windows Application

Here is a extremely simple WinForms app which simply shows a MessageBox when a button is clicked

open System
open System.Windows.Forms

[<EntryPoint>]
let main argv =

    let bufferData = Array.zeroCreate<byte> 100000000

    let form = new Form(Text = "Test Form")
    let button = new Button(Text = "Start")
    form.Controls.Add(button)
    button.Click.Add(fun args -> MessageBox.Show("button clicked") |> ignore)
    Application.Run(form)
    //return 0 for main method
    0       

Which when runs will give you something like this (providing you clicked the button that is)

image

 

Creating A Simple WPF App With F#

F# can also be used to create Silverlight/WPF/WinRt apps. Unfortunately there is no inbuilt support for this, but as long as you know the Dlls to use you can get through this hurdle. There is one key difference when using F# compared to C#/VB .NET, which is in both of those language there are lovely nice integrated Visual Studio templates, which allow you to add a new Window/UserControl, which will generate a partial class with 2 parts

  • The XAML designer part
  • The code behind which has the InitialiseComponent() which will result in the correct compiler generated file being created

In F# you MUST create a simple .xaml file which is best made by adding a new Text file to your F# project and then renaming it. You MUST then load the XAML up the  XamlReader.Load to create a Window.

This small demo I have put together attempts to follow current XAML development best practices, which are to use the MVVM pattern. As such you can expect to see code for

  • INPC base class that implements the INotifyPropertyChanged interface
  • DelegateCommand which allows you to create a ICommand implementation where the CanExecute()/Execute methods are handled in your own ViewModel code
  • A ViewModel
  • A View

I have taken some of the code here from F# industry leaders like Phil Trelford, from the F# snippets

INPC Base Class

The base class code is Phil Trelfords original code that is available right here : http://fssnip.net/2x and it looks like this

//Phil Trelfords ObservableObject : http://fssnip.net/2x
type ObservableObject () =
    let propertyChanged =
        Event<PropertyChangedEventHandler,PropertyChangedEventArgs>()
    let getPropertyName = function
        | PropertyGet(_,pi,_) -> pi.Name
        | _ -> invalidOp "Expecting property getter expression"
    interface INotifyPropertyChanged with
        [<CLIEvent>]
        member this.PropertyChanged = propertyChanged.Publish
    member this.NotifyPropertyChanged propertyName =
        propertyChanged.Trigger(this,PropertyChangedEventArgs(propertyName))
    member this.NotifyPropertyChanged quotation =
        quotation |> getPropertyName |> this.NotifyPropertyChanged

Delegate Command Implementation

This was taken from the following Url : http://geekswithblogs.net/MarkPearl/archive/2010/06/17/yippy-ndash-the-f-mvvm-pattern.aspx, and looks like this

type DelegateCommand (canExec:(obj -> bool), doExec:(obj -> unit)) =
    let canExecuteEvent = new DelegateEvent<EventHandler>()
    interface ICommand with
        [<CLIEvent>]
        member x.CanExecuteChanged = canExecuteEvent.Publish
        member x.CanExecute arg = canExec(arg)
        member x.Execute arg = doExec(arg)

ViewModel

Having these helpers in place, then allows you to create a ViewModel that has your custom properties/commands that the View will bind to. Here is a very simple example ViewModel:

//An example ViewModel
type MainWindowViewModel () =
    inherit ObservableObject()
    let mutable message = "Yo I am from the ViewModel"
    let mutable currentItem = ""

    let items = new List<string>()

    do items.Add("Who laughing now")
    do items.Add("The cat barked")
    do items.Add("Batman is here")

    let showMessage(msg) =
        let msg = MessageBox.Show(msg)
        ()    

    member this.Items
        with get () = items

    member this.Message
        with get () = message
        and set value =
            message <- value
            this.NotifyPropertyChanged <@ this.Message @>

    member this.CurrentItem
        with get () = currentItem
        and set value =
            currentItem <- value
            this.NotifyPropertyChanged <@ this.CurrentItem @>

    member this.ShowMessageCommand =
            new DelegateCommand
                (
                    (fun d -> true),
                    (fun e -> showMessage(this.Message))
                )

    member this.ShowCurrentItemCommand =
            new DelegateCommand
                (
                    (fun d -> true),
                    (fun e -> showMessage(this.CurrentItem))
                )

View

As previously stated the View must be loaded using the XAMLReader.Load() function. This then creates the Window (view) from the XAML. We then create a new ViewModel and set that as the DataContext for the Window, to facilitate binding from the View to the ViewModel. Here is the relevant code to do this:

open System
open System.Reflection
open System.Windows
open System.Windows.Markup
open WPFAppDemo.ViewModels

let mainWindowStream = Assembly.GetExecutingAssembly().GetManifestResourceStream("MainWindow.xaml")
let mainWindow =
    let win = XamlReader.Load(mainWindowStream) :?> Window
    let viewModel = new MainWindowViewModel()
    win.DataContext <- viewModel
    win

let app = new Application()

[<STAThread>]
app.Run mainWindow |> ignore

Where the View that binds to the ViewModel (which is set as the DataContext for the View)

<Window xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation&quot;
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml&quot;
        Title="MainWindow" Height="350" Width="525">
    <StackPanel Orientation="Vertical">
        <TextBox FontSize="14" Text="{Binding Message}" Margin="10"/>
        <Button Content="Show Message" Command="{Binding ShowMessageCommand}" Margin="10"/>
        <ListBox ItemsSource="{Binding Items}" SelectedItem="{Binding CurrentItem}" Margin="10"/>
        <Button Content="Show Current Item" Command="{Binding ShowCurrentItemCommand}" Margin="10"/>
    </StackPanel>
</Window>

Call A C# Method From F#

It should come as no surprise that F# can call a method created in a C# dll. Here is some demo code that proves this.

We have this C# code, which will be called via F#

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.NetworkInformation;
using System.Text;
using System.Threading.Tasks;

namespace CSharpCommon
{
    public class Class1
    {
        public IEnumerable<string> GetEnumerable(int number, string prefix)
        {
            return Enumerable.Range(0, number)
                    .Select(x => string.Format("CSharpCommon.Class1.ListItem : {0}", x.ToString()));
        }
    }
}

And here is the F# code that calls this:

open System

//use the C# Dll
open CSharpCommon

[<EntryPoint>]
let main argv =
    printfn "%A" argv

    //Call the C# function from F#
    let class1 = new CSharpCommon.Class1()
    let list = class1.GetEnumerable(10,"Called from F#") |> Seq.iter (fun x -> printfn "item: %s" x)

    Console.ReadLine() |> ignore

    0 // return an integer exit code

Which when run gives this result:

image

Call A F# Function From C#

Likewise it should come as no surprise that C# can call a method created in a F# dll. Here is some demo code that proves this.

We have this F# code, which will be called via C#

namespace FSharpCommon
    module CustomTypes =

        open System
        
        let GetEnumerable(number : int, prefix : string) =
            seq { for i in 1 .. number do yield String.Format("FSharpCommon.CustomTypes.ListItem : {0}", i)}
          

And here is the C# code that calls this:

using System;

//use the F# Dll
using FSharpCommon;

namespace CSharpConsoleCallsFSharp
{
    class Program
    {
        static void Main(string[] args)
        {
            //Call the F# function from C#
            foreach (var item in CustomTypes.GetEnumerable(10, "Called from C#"))
            {
                Console.WriteLine(String.Format("item: {0}", item));
            }
            Console.ReadLine();
        }
    }
}

Which when run gives this result:

image

Calling A Native Dll From F#

As some of you may know there has long been a way to call native Dlls. Native Dlls are the ones that come with Windows. This technique of calling native Dlls is known as Platform Invoke (or PInvoke for short). It is quite useful occasionally and can get you out of some funny little scrapes at time. As far as I recall it has support all the way back to VB6 (may be even earlier). The problem with calling PInvoke methods is that you are then tying yourself well and truly to ONLY being able to run your code on Windows, as this is the only place the native Dlls exist that you are calling.

That said I still think it is good to cover this technique. I have deliberately chosen a very simple native function to call, as some of the PInvoke signatures can get a little hairy.

The function I have chosen to use is the Kernel32.dll Beep function. You can read more about it using the great PInvoke resource PInvoke.net. The Beep function is detailed here : http://www.pinvoke.net/default.aspx/kernel32.beep

Before we get into the F# code, I just wanted to show what it would look like to call this function from C#, which would be done as follows:

using System;
using System.Runtime.InteropServices;

class BeepSample
{
    [DllImport("kernel32.dll", SetLastError=true)]
    static extern bool Beep(uint dwFreq, uint dwDuration);

    static void Main()
    {
            Beep(100, 5);
    }
}

 

And here is the same Native code using F#, where we have placed the code within a module. There are some subtle differences between the C# code and the F# code, this is all explained in the comments within the code block below. The PInvoke.net is still a very good starting place when you want to use some PInvoke in F#.

namespace ConsoleApplication1
    module CustomTypes =

        open System.Runtime.InteropServices
        open System

            // NOTE : This is how to use a simple P/Invoke example from F#
            // There are a couple of things to note here
            // 1. The Beep function actually declares a return type, this is abnormal for F# function
            // 2. When compared to the C# code shown below (commented out) the F# MarshalAs, MUST appear
            //    on the actual return value
            // 3. The argument do NOT follow the F# convention of argName : argType
            [<DllImport("kernel32.dll", SetLastError=true)>]
            extern [<MarshalAs(UnmanagedType.Bool)>]
                bool Beep(System.UInt32 dwFreq, System.UInt32 dwDuration)

Which can then be used like this

open System
open ConsoleApplication1.CustomTypes

[<EntryPoint>]
let main argv =

    printfn "About to beep" |> ignore

    //beep
    ConsoleApplication1.CustomTypes.Beep(2500u, 300u) |> ignore

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

F# 28 : Integrating With Task Parallel Library

Last time we looked at the Async class, and examined some of its core functions. This time we will be looking at using some Task Parallel Library (TPL) classes, namely Task<T>, and Task. We will also examine how the Async module can be used in conjunction with TPL. 

TPL Primer

I do not have enough time in this post to go through all the nitty gritty details of TPL, but I will just mention a few key points

  • TPL uses a Task<T> to represent a asynchronous operation that will return a value T in this case (yes a generic so anything your heart desires)
  • TPL uses a Task to represent a asynchronous operation that doesn’t return a value. Unit in F# lingo
  • In TPL there are several trigger values that cause the Task<T> to be observed. Things like Wait / WaitAll / Result will also cause the tasks to be observed. These are however blocking operations that suspend the calling thread.
  • TPL may also use CancellationTokens to cancel async operations (albeit you need a bit more code in C# than you do in F# due to the fact that in C# you must constantly check the CancellationToken, which we saw in the previous post)
  • Both Task<T> and Task can be waited on
  • Both Task<T> and Task can run things known as continuations, which are essentially callbacks when the Task<T> / Task is done. You may schedule callback for when a Task ran to completion, or is faulted, or both, or none
  • Task<T> and Task for the basis of the new async/await syntax in C#

Starting And Waiting For Task<T>

In this simple example we will show how to create a simple Task<T> that returns a boolean. We will the use the blocking Task<T>.Wait() method, to obtain the result of the Task<T>, which will be a boolean in this case.

open System
open System.Threading
open System.Threading.Tasks

[<EntryPoint>]
let main argv =

    let work() =
        for i in 0 .. 2 do
            printfn "Work loop is currently %O" i |> ignore
            Thread.Sleep(1000)
        false
    
    printfn "Starting task that returns a value" |> ignore
    let task = Task.Factory.StartNew<bool>((fun () -> work()),  TaskCreationOptions.LongRunning)
    let result = task.Result
    printfn "Task result is %O" result
   
    Console.ReadLine() |> ignore
    
    //return 0 for main method
    0       

Which when run gives the following output

image

We could also do this another way too which would yield the same results. We could use a continuation from the original Task<T> that is run when the original task runs to completion. Think of continuations as callbacks. Here is the code rewritten to use a continuation, remember you can have a single callback for the whole original task, or hook up specific ones for particular scenarios, which is what I have done here.

 

open System
open System.Threading
open System.Threading.Tasks

[<EntryPoint>]
let main argv =

    let work() =
        for i in 0 .. 2 do
            printfn "Work loop is currently %O" i |> ignore
            Thread.Sleep(1000)
        false
    
    printfn "Starting task that returns a value" |> ignore
    let task = Task.Factory.StartNew<bool>((fun () -> work()),  TaskCreationOptions.LongRunning)
    task.ContinueWith((fun (antecedant : Task<bool>) -> printfn "Task result is %O" antecedant.Result),
        TaskContinuationOptions.OnlyOnRanToCompletion) |> ignore
   
    Console.ReadLine() |> ignore
    
    //return 0 for main method
    0       

Starting And Waiting For Task<T> In A More F# Like Way

The Async class offers a couple of helpers when dealing with tasks, you may use

  • Async.StartAsTask
  • Async.AwaitTask

Here is some code that shows how you can use these

open System
open System.Threading
open System.Threading.Tasks

[<EntryPoint>]
let main argv =

    let work = async {
        for i in 0 .. 2 do
            printfn "Work loop is currently %O" i |> ignore
            do! Async.Sleep(1000)
        return "task is completed " + DateTime.Now.ToLongTimeString()
        }
    
    printfn "Starting task that returns a value" |> ignore
   
    let asynWorkflow = async {
        //NOTE : Async.StartAsNewTask doesn't like TaskCreationOptions.LongRunning
        let task = Async.StartAsTask((work))
        let! result = Async.AwaitTask(task)
        return result
    }

    let finalResult = Async.RunSynchronously asynWorkflow
    printfn "Task result is : %O" finalResult
   
    Console.ReadLine() |> ignore
    
    //return 0 for main method
    0       

 

Here are the results of running the above code:

image

 

Starting And Waiting For Plain Task

Another thing you might find yourself wanting to do is a use a TPL Task. That is a Task that does not return a value, basically you have Task<T> which is a task that returns T, and Task (essentially Task void, or Task<Unit> in F# lingo), which is a task that doesn’t return a value. Task may still be waited on in C# land, but there seems to be less you can do with a standard Task (one that doesn’t return a value) in F#.

There however a few tricks you can do, the first one requires a bit of insight into multi threading anyway, which is that Task, and Task<T> for that matter both implement IAsyncResult, which is something you can wait on inside of a F# async workflow, by using Async.AwaitIAsyncResult. Here is a small example, of how you can wait on a plain Task. This example also demonstrates how you can extend the Async module to include your own user specified functions. That is pretty cool actually, C# allows extension methods (which F# also allows), but being able to just add arbitrary functions is very cool.

Anyway here is the code:

open System
open System.Threading
open System.Threading.Tasks

//This extends the Async module to add the
//AwaitTaskVoid function, which will now appear
//in intellisense
module Async =
    let AwaitVoidTask : (Task -> Async<unit>) =
        Async.AwaitIAsyncResult >> Async.Ignore

[<EntryPoint>]
let main argv =

    let theWorkflow(delay :int) = async {
        printfn "Starting workflow at %O" (DateTime.Now.ToLongTimeString())
        do! Task.Delay(delay) |> Async.AwaitVoidTask
        printfn "Ending workflow at %O" (DateTime.Now.ToLongTimeString())
    }
    
    Async.RunSynchronously (theWorkflow(2000))

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

Which when run gives the following result:

image

Some other clever chap who maintains this blog https://gist.github.com/theburningmonk/3921623 has a slightly different take on this. Here is his version, which I also think has many merits, for example it is really nice that it will pattern match against a Faulted Task and raise an Exception

open System
open System.Threading
open System.Threading.Tasks

//This extends the Async module to add the
//AwaitTaskVoid function, which will now appear
//in intellisense
module Async =
    let inline awaitPlainTask (task: Task) =
        // rethrow exception from preceding task if it fauled
        let continuation (t : Task) : unit =
            match t.IsFaulted with
            | true -> raise t.Exception
            | arg -> ()
        task.ContinueWith continuation |> Async.AwaitTask

    let inline startAsPlainTask (work : Async<unit>) =
        Task.Factory.StartNew(fun () -> work |> Async.RunSynchronously)

[<EntryPoint>]
let main argv =

    let sleepy = async {
        do! Async.Sleep(5000) // sleep for 5 seconds
        printfn "awake"
      }

    let sleepy2 = async {
        do! sleepy |> Async.startAsPlainTask |> Async.awaitPlainTask
        printfn "feeling sleepy again…"
      }

    //call the workflows
    sleepy |> Async.startAsPlainTask |> ignore
    sleepy2 |> Async.Start |> ignore

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

Which gives the following results when run:

image

 

Starting And Waiting For Multiple Tasks

To wait for multiple Task<T> you can use TPLs Task.WhenAll() for this, which will give you an aggregated result task, which will have a result object which contains the results from the original tasks you used in the Task.WaitAll() call.

There may well be a way that you can bend the Async.Parallel() to do the same job, but to my mind using Task.WhenAll() is by far the easiest way.

Here is some code that demonstrates this

open System
open System.Threading
open System.Threading.Tasks

[<EntryPoint>]
let main argv =

    let work(msg) =
        for i in 0 .. 2 do
            printfn "%O : Work loop is currently %O\r\n" msg i |> ignore
            Thread.Sleep(1000)
        "Task 1 done " + (DateTime.Now.ToLongTimeString())

    let taskRunner(msg) =
        printfn "Starting %O that returns a value %O\r\n" msg (DateTime.Now.ToLongTimeString()) |> ignore
        Task.Factory.StartNew<string>((fun () -> work(msg)),  TaskCreationOptions.LongRunning)
     
    
    let task1 = taskRunner("task1")
    Thread.Sleep(2000)
    let task2 = taskRunner("task2")
    Thread.Sleep(2000)
    let task3 = taskRunner("task3")

    let resultsOfAllTask = Task.WhenAll([task1;task2;task3])

    printfn "Task1 result: %O\r\nTask2 result: %O\r\nTask3 result: %O"
        resultsOfAllTask.Result.[0]
        resultsOfAllTask.Result.[1]
        resultsOfAllTask.Result.[2]
    
    Console.ReadLine() |> ignore
    
    //return 0 for main method
    0       

 

Which when run will give the following results

image

 

F#27 : Asynchronous Workflows

Last time we looked at reactive programming, and this time we will look at a very cool feature of F# which is called asynchronous workflows. It is fair to say that the new Async-Await syntax bears more than a passing resemblance to F# async workflows.

Async workflows offer a easy way to write asynchronous code in F# that perform some background task, and have a lot of helper functions to manage them using the Async class.

The Async Class

The Async class has a whole load of functions that allow you to write async code. Here is a table which shows the functions that you are free to use. We will be looking at some of these

 

image

 

 

And here are an example or 2 of how you might use some of these functions

Async.AwaitEvent

In this small example, we create a Timer, and then using the Async class’s Async.AwaitEvent(..), which will return a Async<T>. This essentially created a thread pool thread to do the work, and then we carry on, and do some more stuff, and finally we use Async.RunSynchronously to await the original Async<T> created by the Async.AwaitEvent(..) call.

Here is the code:

open System
open System.IO
open System
open System.Linq
open System.Collections.Generic
open Microsoft.FSharp.Control

[<EntryPoint>]
let main argv =

    let waitForTimerEvent(timeout) =

        // create a timer and associated async event
        let timer = new System.Timers.Timer(timeout)

        //async computation that waits of a particualt CLI Event to occur
        let timerEvent = Async.AwaitEvent (timer.Elapsed) |> Async.Ignore

        printfn "Time now: %O" DateTime.Now.TimeOfDay
        timer.Start()

        printfn "do other stuff"

        //blocks waiting for the timer tick, this is pretty
        //much the same as await someTask in async/await
        Async.RunSynchronously timerEvent

        printfn "Time Is Done at time: %O" DateTime.Now.TimeOfDay

        Console.ReadLine() |> ignore

    waitForTimerEvent 5000.0

    //return 0 for main method
    0       

The output may help to clarify this a bit:

image

Async.AwaitIAsyncResult

Here is another example (from MSDN) that shows how the Async class also offers function for creating Async<T> values from the common APM (BeginSomeMethod()/EndSomeMethod(IAsyncResult…)). It can be seen that this example uses the Async class to both write and read to a text file asynchronously. It does introduce a bit of extra syntax by way of the “Let!” which I will be getting to in just a minute

open System
open System.IO
open System
open System.Linq
open System.Collections.Generic
open Microsoft.FSharp.Control

[<EntryPoint>]
let main argv =

    let streamWriter1 = File.CreateText("test1.txt")
    let count = 10000000
    let buffer = Array.init count (fun index -> byte (index % 256))

    printfn "Writing to file test1.txt."
    let asyncResult = streamWriter1.BaseStream.BeginWrite(buffer, 0, count, null, null)

    // Read a file, but use AwaitIAsyncResult to wait for the write operation
    // to be completed before reading.
    let readFile filename asyncResult count =
        async {
            //write the file but do not continue until we have done so
            let! returnValue = Async.AwaitIAsyncResult(asyncResult)
            //wait for the file to be written before we read it, again this is like
            //await File.WriteAllTextAync(…) in async/await land
            printfn "Reading from file test1.txt."
            // Close the file.
            streamWriter1.Close()
            // Now open the same file for reading.
            let streamReader1 = File.OpenText(filename)
            let! newBuffer = streamReader1.BaseStream.AsyncRead(count)
            return newBuffer
        }

    let bufferResult = readFile "test1.txt" asyncResult count
                       |> Async.RunSynchronously

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

Which when run will give the following results:

image

A Rather Nice UI Example

Credit where credit is due, I do a lot of UI work, and I have to say that the MSDN example on how to use some of the Async class functions in this area is first rate. This small example shows how to use the following Async class functions

  • Async.SwitchToThreadPool()
  • Async.SwitchToContext()
  • Async.StartImmediate(…)

 

Here is the relevant code:

open System.Windows.Forms

open System.Windows.Forms

[<EntryPoint>]
let main argv =

    let bufferData = Array.zeroCreate<byte> 100000000

    let async1 (button : Button) =
         async {
           button.Text <- "Busy"
           button.Enabled <- false
           do! Async.Sleep 5000
           let context = System.Threading.SynchronizationContext.Current
           do! Async.SwitchToThreadPool()
           use outputFile = System.IO.File.Create("longoutput.dat")
           do! outputFile.AsyncWrite(bufferData)
           do! Async.SwitchToContext(context)
           button.Text <- "Start"
           button.Enabled <- true
           MessageBox.Show("Done") |> ignore
         }

    let form = new Form(Text = "Test Form")
    let button = new Button(Text = "Start")
    form.Controls.Add(button)
    button.Click.Add(fun args -> Async.StartImmediate(async1 button))
    Application.Run(form)
    //return 0 for main method
    0       

 

So what exactly is going on here? Well as any winforms/WPF/Silverlight or Window8 developer knows, you must update UI controls on the thread that created them, so this code deals with that, by way of a SychnorizationContext which is the standard winforms way of posting delegates/actions to the correct thread. Lets walk through it

  1. Button is clicked on UI thread, which starts workflow using Async.StartImmediate which is in current thread (the UI thread)
  2. Async workflow starts, and sets some form control values, which is ok as it is still the UI thread at this point
  3. We then store the windows forms SynchronizationContext to allow us to marshall calls back to the UI thread later
  4. We then switch to a threadpool thread using Async.SwitchToThreadPool()
  5. We do some async work where we write to a file
  6. We then switch back to the UI thread using the SynchronizationContext we stored earlier, and use the Async.SwitchToContext() function
  7. We then set some form control values, which is ok at this point as we are now back on the UI thread thanks to the switch to the previously stored SynchronizationContext

 

Anyway here is the results of this code, After we click the button and trigger the async workflow

image

And when the async workflow has completed

image

This example did introduce a bit too much syntax, but we are just about to look into this so I hope you can forgive me that slight indulgence.

 

 

Starting Async Workflows Manually

As well as the inbuilt functions of the Async class, you can also manually create your own async workflows. Async workflows generally follow this syntax when created manually.

async { expression }

Using this syntax, the expression is some computation that will run asynchronously. This means it will not block the current computation/thread. The type of the expression is Async<‘a>. There are many different ways of creating asynchronous code in F#, and you may use any of the types/functions which are available . The Async class is the best place to start.

F# async workflows allow synchronous and asynchronous operations to be used within the same workflow. They also come with their own set of syntax that can be used in the construction of workflows. Using thee following keywords (be careful though they are quite similar to the non async versions that you have already seen), you are able to create complete workflows, which may/may not contain a mixture of async code and synchronous code.

let!

Allows you to effectively wait for async results. It has the effect that the right hand side of the Let! must return before the rest of the async workflow continues

use!

The object is disposed of at the close of the current scope.

do!

The same as its counter part “do”, but is intended to be used inside async workflows

Here is a small manually created async workflow, that does nothing more than sleep inside of it

open System

[<EntryPoint>]
let main argv =

    let sleepAsync(timeout) =
        //this is the manual async workflow
        let sleeper = async {
            printfn "Before sleep %O" (DateTime.Now.ToLongTimeString())
            do! Async.Sleep timeout
            printfn "After sleep %O" (DateTime.Now.ToLongTimeString())
        }

        //wait on the sleeper (where sleeper is Async<T>)
        Async.RunSynchronously sleeper

        printfn "Async worflow completed"
        

    //call the function that contains the async workflow
    sleepAsync(5000)a

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

Which produces the following results when run

image

You may also nest workflows, which means that you may manually create or trigger async workflows from within workflows (kind of like inception, if you have seen it). Anyway here is an example of that, where we create a child workflow using our previous timer example, and then have a parent workflow use this child workflow.

open System

[<EntryPoint>]
let main argv =

    //Child workflow
    let timerWorkflow = async {
        let timer = new System.Timers.Timer(5000.0)
        let timerEvent = Async.AwaitEvent (timer.Elapsed) |> Async.Ignore
        timer.Start()

        //wait for the timer Async<T>
        Async.RunSynchronously timerEvent
    }

    //Parent workflow
    let parentWorkflow  = async{

        printfn "Starting parent at : %O" (DateTime.Now.ToLongTimeString())
        let! childTimerWorkflow = Async.StartChild timerWorkflow

        printfn "parentWorkflow is about to wait for a bit at : %O" (DateTime.Now.ToLongTimeString())
        do! Async.Sleep 2000
        printfn "parentWorkflow continues to do stuff at : %O" (DateTime.Now.ToLongTimeString())
        
        // use let! to wait for the childTimerWorkflow
        let! result = childTimerWorkflow

        printfn "parentWorkflow completed at : %O" (DateTime.Now.ToLongTimeString())
    }

    // run the parentWorkflow
    Async.RunSynchronously parentWorkflow  

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

Which when run gives the following result

image

 

Cancellation Of Workflows

You may also use the standard TPL type of cancellation to cancel an async workfow. That is one where you use a CancellationTokenSource to provide a CancellationToken to the async workflow, which you may then use to cancel the work flow with.

Here is some code that demonstrates this technique.

open System
open System.Threading

[<EntryPoint>]
let main argv =

    //Child workflow
    let timerWorkflow = async {

        for i in 0..9999 do
            printfn "Start is %d" i
            do! Async.Sleep(1000)
            printfn "Done is %d" i
  
    }

    
    let cts = new CancellationTokenSource()

    // start the timerWorkflow but pass in the CancellationToken
    Async.Start (timerWorkflow,cts.Token)

    //wait 1 second then cancel the token
    Thread.Sleep(2000)  

    printfn "Cancelling" |> ignore
    cts.Cancel()

    printfn "Cancelled" |> ignore

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

Which when run gives the follow results

image

The eagle eyed amongst you will notice that I did not have to do anything specific with the CancellationToken inside the workflow itself, in F# this is all just handled for you. If you compare that to the C# equivalent (Ok we could use Parrallel.For(..) but for this demo I did not) you will see there is a lot more C# code

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace ConsoleApplication5
{
    class Program
    {
        static void Main(string[] args)
        {

            var tcs = new CancellationTokenSource();
            var token = tcs.Token;

            var task = Task.Factory.StartNew(() =>
                {
                    token.ThrowIfCancellationRequested();
                    for (int i = 0; i < 9999; i++)
                    {
                        
                        Console.WriteLine(string.Format("Start is : {0}", i));
                        Thread.Sleep(1000);
                        Console.WriteLine(string.Format("Done is : {0}", i));
                        if(token.IsCancellationRequested)
                            token.ThrowIfCancellationRequested();
                    
                    }
                }, token);

            tcs.Cancel();

            try
            {
                task.Wait();
            }
            catch(AggregateException aex)
            {
                foreach (var ex in aex.InnerExceptions)
                {
                    Console.WriteLine(aex.Message + " " + ex.Message);
                }
            }

            Console.ReadKey();
        }
    }
}

Waiting For Cancelled Async WorkFlow

One thing that struck me as very odd is that if I was using  C# I would still be able to know about a cancelled Task in TPL land, by wait of a continuation that only runs on Cancelled State, or I could use a Wait with a Try-Catch which caught AggregateException (much like the sample shown above), and using async/await it is even easier.

Anyway my point being in C#, I would have no problems waiting on a cancellable task, there are many ways, but I could not seem to find a way to do that in F#. So I did some googling and low and behold Tomas Petricek has done some code that allows you to do that which you can find at this url: http://www.fssnip.net/d4, I got to this link from this Stack Overflow discussion : http://stackoverflow.com/questions/11609089/waiting-on-the-cancellation-of-an-asynchronous-workflow

His code is complex and probably not best suited to a beginners guide, but it is worth looking at if that is what you are after.

 

Serial Workflows

You can of course run async workflows in series, where you just wait for one workflow to complete using “let!”, here is a small example:

open System
open System.Threading

[<EntryPoint>]
let main argv =

    let looper = async {
        for i in 0..3 do
            printfn "Start is %d" i
            do! Async.Sleep(500)
            printfn "Done is %d" i
    }

    //runs 2 async workflows one after another   
    let run2WorkflowsInSeries = async {
        let! loop1 = looper
        printfn "Done loop1"
        let! loop2 = looper
        printfn "Done loop2"
    }
   

    Async.RunSynchronously run2WorkflowsInSeries
    printfn "All done"

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

Which when runs gives the following output:

image

 

Parallel Workflows

It is also entirely possible to run async workflows using a parallel type arrangement. If I was using TPL in C#, this would be the equivalent of Task.WhenAll(..) / Task.WaitAll(..). I have shameless stolen the following code snippet from Tomas Petriceks blog, which you can find right here, I urge you to read this read this blog, it is very very interesting : http://tomasp.net/blog/csharp-fsharp-async-intro.aspx/

Here is the code, which demonstrates how to run async workflows in parallel

open System
open System.Threading
open System.Text.RegularExpressions
open System.Net
open System.IO

[<EntryPoint>]
let main argv =
    
    let regTitle = new Regex(@"\<title\>([^\<]+)\</title\>")
  
    /// Asynchronously downloads a web page and returns
    /// title of the page and size in bytes
    let downloadPage(url:string) = async {
        let request = HttpWebRequest.Create(url)
        // Asynchronously get response and dispose it when we're done
        use! response = request.AsyncGetResponse()
        use stream = response.GetResponseStream()
        let temp = new MemoryStream()
        let buffer = Array.zeroCreate 4096

        // Loop that downloads page into a buffer (could use 'while'
        // but recursion is more typical for functional language)
        let rec download() = async {
            let! count = stream.AsyncRead(buffer, 0, buffer.Length)
            do! temp.AsyncWrite(buffer, 0, count)
            if count > 0 then return! download() }
   
        // Start the download asynchronously and handle results
        do! download()
        temp.Seek(0L, SeekOrigin.Begin) |> ignore
        let html = (new StreamReader(temp)).ReadToEnd()
        return regTitle.Match(html).Groups.[1].Value, html.Length }

    // Downloads pages in parallel and prints all results
    let comparePages = async {
        //wait for all results, similar to Task.WhenAll
        let! results =
            [| "http://www.google.com&quot;;
                "http://www.bing.com&quot;;
                "http://www.yahoo.com&quot; |]
            |> Array.map downloadPage
            |> Async.Parallel
        for title, length in results do
            Console.WriteLine("{0} (length {1})", title, length)
    }

    // Start the computation on current thread
    do comparePages |> Async.RunSynchronously

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

Which when run produces the following results:

image

 

Further Reading : The F# Asynchronous Programming Model

Read more from the F# language creator, and main researcher, Don Syme and Tomas Petricek, I urge you all to go off and read the PDF at this link : http://research.microsoft.com/apps/pubs/default.aspx?id=147194

F#26 : Reactive Programming

In this post we will look at using a reactive programming paradigm within F#. There may be some of you that have used the Reactive Extensions (Rx), I am in fact a massive fan boy of Rx, and really enjoy what it can bring to a project, in particular I think a UI project benefits immensely from a more reactive approach.

There may of course be those of you that have never come across Rx at all. So lets take a very small detour and talk about the general idea of the observer pattern.

Observer Pattern

Lets say I have order system that should print invoices and also send emails to a client when a new order is received. A naive implementation of this may be to just lump all this into a single class, but this is a poor separation of concerns, we could do better. So what we could do, is to have a order system object which receives orders and then calls into 2 other classes that produce a invoice and send an email to a client.

This is ok, but we would now have to take a strong dependency on the 2 sub systems from the order system class, and then call them when a new order arrives. Wouldn’t it be better if the order system class could just accept a list of subscribers (say implementing some IAcceptOrder interface), and then any time a  new order arrives the order system class would simply loop through its list of subscribers and call their AcceptOrder method (from the hypothetical IAcceptOrder interface).

This is essence is the observer pattern, of course this pattern could also allow unsubscribing too.

Rx has built upon the general idea of the observer pattern, and has added a great many standard .NET classes that aid in the construction of observable streams of data. You can also use subscriptions over events, asynchronous operations, and also use the standard LINQ operators.

So that is what Rx gives you.

F# also comes with a Control.Observable /Control.Event modules which contains many types that can be used to create reactive code The types and functions in this module mirror some of the functionality found in the Rx classes (see http://msdn.microsoft.com/en-us/library/system.reactive.linq.observable(v=vs.103).aspx).

This article is however about F#, so we will be keeping the discussion from here on out about the F# Observable modules.

 

Observable Module

The F# Observable module is the place to start for reactive programming in F#, and contains the following functions/types

image

We will be seeing some examples of these is just a minute, but before we do it is worth just going on another slight detour. So lets just get the slight detour over with before we start to look at the Observable module in depth.

<SlightDetour>

There were several things that made Rx so powerful :

  • The ability to treat events as a source to create an IObservable<T>. This IObservable<T> could then have any of the standard LINQ operators applied to it, along with another specific set of IObservable<T> extension methods. This is a very powerful technique, which allows you to do things like only listen to an event where some condition is true, project the original event args into a completely new type, merge 2 or more events into a single stream (this technique is particularly powerful when building UIs, I use this one a lot)
  • The decoupling of the event into a much for general purpose interface (IObservable<T>), which means that users of the original event source dino longer need a direct link to the original event source class (which they would do if they wanted to add an event handler to the source object event). Depending on a abstraction, i.e IObservable<T> is a much better / cleaner design. IObservable<T> is a base class type that is included in the .NET framework
  • The ability to subscribe, which would return a IDisposable, which you could then just wrap in a using(..) or Dispose of when you were done with it, both of which would stop the subscriber from receiving any further notifications

The F# team (Don Syme I guess here), have exposed some (though not all) of the Rx goodness in F# so it is important to understand some of the reasons why IObservable<T> is so useful.

</SlightDetour>

OK now that we have talked about why IObservable is better than a plain old event, lets have a look at some examples using the F# Observable module. Here is a small windows form (yes you can do forms in F# quite easily too) example that demonstrates the following things:

  • How to create an IObservable<’a> from a standard event using Observable.filter, where the filter is just being used to give back a IObservable<’a>, in essence no filtering at all
  • How to use Observable.add to add a handler to an IObservable<’a>
  • How to create an actual filter from an IObservable<’a> using Observable.filter, this filter ensures that only MouseMove events that happen in the bottom 1/2 of the form notify listeners
  • How to create an IDisposable subscription using Observable.subscribe
  • How to cancel a subscription by simply calling Dispose on the subscriber which is an IDisposable. In this example this is done using a Task.Delay(4000), which means the subscriber will only work for 4 seconds, and then will not receive any notifications after that

 

open System
open System.IO
open System
open System.Linq
open System.Collections.Generic
open ConsoleApplication1.CustomTypes
open System.IO
open System.Drawing
open System.Windows.Forms
open System.Threading.Tasks

[<EntryPoint>]
let main argv =

    //create a form
    let form = new Form(Text = "F# Windows Form",
                        Visible = true,
                        TopMost = true)

    let label1 = new Label()
    label1.Text <- "Label1"
    label1.Location <- new Point(10,10)

    let txt1 = new TextBox()
    txt1.Width <- 160
    txt1.Location <- new Point(120,10)

    let label2 = new Label()
    label2.Text <- "Label2"
    label2.Location <- new Point(10,40)

    let txt2 = new TextBox()
    txt2.Width <- 160
    txt2.Location <- new Point(120,40)

    form.Controls.Add(label1)
    form.Controls.Add(txt1)
    form.Controls.Add(label2)
    form.Controls.Add(txt2)

    //use Control.Observable reactive functions
    form.MouseMove
        |> Observable.filter ( fun evArgs -> true)
        |> Observable.add ( fun evArgs ->
            txt1.Text <- String.Format("x: {0} y :{1}", evArgs.X, evArgs.Y))

    //shows how to subscribe, such that we get a IDisposable back for subscription
    let sub =
        form.MouseMove
        |> Observable.filter ( fun evArgs -> evArgs.Y > form.Height / 2)
        |> Observable.subscribe  ( fun evArgs ->
            txt2.Text <- String.Format("x: {0} y :{1}", evArgs.X, evArgs.Y))

    //dispose of the subsriber after 4 seconds
    Task.Delay(4000).ContinueWith(fun x -> sub.Dispose()) |> ignore

    //run the windows form message pump
    Application.Run(form)

    //return 0 for main method
    0       

Which when runs looks like this:

image

With this one I urge you to try the code out for yourself, as you will not be able to see that the Label2 associated TextBox stops updating after 4 seconds in a screen shot

This is cool for sure, but the real power of IObservable is that you can use it against your own events/properties too, so lets wrap up this post by looking at an example where we create our own event source, and look at a few more of the Observable module functions.

Here is a small class that contains a single “NewOrderEvent”, which uses a custom EventArgs derived class called “OrderEventArgs”. The “OrderEventArgs” has the following 2 properties:

  1. Price : decimal
  2. AuthorisationLevel : Which uses a empty discriminating union type called “DiscountApprovalLevel”.

Here  is the relevant code:

namespace ConsoleApplication1
    module CustomTypes =

        open System
        open System.Collections.Generic
        open System.ComponentModel
        open System.Reflection

        type DiscountApprovalLevel = Standard | Manager | Ceo

        type Order = { Price : decimal; AuthorisationLevel : DiscountApprovalLevel }

        type OrderArgs(price : decimal, authorisationLevel : DiscountApprovalLevel) =
            inherit System.EventArgs()
    
            member this.Price = price
            member this.AuthorisationLevel = authorisationLevel

        type OrderChangeDelegate = delegate of obj * OrderArgs -> unit

        type OrderSystem() =
            let newOrderEvent = new Event<OrderChangeDelegate, OrderArgs>()
    
            member this.CreateOrder(order) =
                newOrderEvent.Trigger(
                    this,
                    new OrderArgs(order.Price, order.AuthorisationLevel)
                )
    
            [<CLIEvent>]
            member this.NewOrderEvent = newOrderEvent.Publish

So that is the code for the source of the custom event, so how about the Observable code, lets see that next:

open System
open System.IO
open System
open System.Linq
open System.Collections.Generic
open ConsoleApplication1.CustomTypes
open System.IO

[<EntryPoint>]
let main argv =

    // Use the Observable module to only subscribe to specific events
    let orderSystem = new OrderSystem()

    let stdDiscountObservable, managerApprovalObservable =
        orderSystem.NewOrderEvent
        // Filter event to just Standard Or Manager level authorisation orders
        |> Observable.filter(fun orderArgs ->
                match orderArgs.AuthorisationLevel with
                | Standard | Manager -> true
                | _ -> false)
        // Split the event into 'Standard' and Other discount approval level
        |> Observable.partition(fun orderArgs ->
                orderArgs.AuthorisationLevel  = DiscountApprovalLevel.Standard)

    // Add event handlers to the stdDiscountObservable IObservable<OrderEventArgs> stream
    stdDiscountObservable.Add(fun args -> printfn "Price : %A, Level : %A" args.Price args.AuthorisationLevel)

    // Add event handlers to the stdDiscountObservable IObservable<OrderEventArgs> stream
      managerApprovalObservable.Add(fun args ->printfn "Price : %A, Level : %A" args.Price args.AuthorisationLevel)

    orderSystem.CreateOrder( { Price = 120.0m; AuthorisationLevel = Manager } )

    //this will not fire any code, as we have filtered out to not include CEO EventArgs
    orderSystem.CreateOrder( { Price = 240.0m; AuthorisationLevel = Ceo } )

    orderSystem.CreateOrder( { Price = 10.0m; AuthorisationLevel = Standard } )
    orderSystem.CreateOrder( { Price = 20.0m; AuthorisationLevel = Standard } )
    orderSystem.CreateOrder( { Price = 50.0m; AuthorisationLevel = Standard } )

    //this will not fire any code, as we have filtered out to not include CEO EventArgs
    orderSystem.CreateOrder( { Price = 240.0m; AuthorisationLevel = Ceo } )

    Console.ReadLine() |> ignore

    //return 0 for main method
    0       

There are several things to point out in this code:

  1. We use a proper Observable.filter this time, such that only “Standard” and “Manager” AuthorisationLevel OrderEventArgs come through the applied filter. This means any event that has OrderEventArgs with a AuthorisationLevel of “Ceo” are effectively ignored thanks to the Observable.filter
  2. We use Observable.partition to partition the source IObservable<OrderEventArgs> into 2 separate IObservable<OrderEventArgs> , one stream for Standard AuthorisationLevel and one stream for Manager AuthorisationLevel. When I say stream I really mean IObservable<T>

Here is what this code looks like when it is run:

 

image

 

Using More Of The Rx Extension Methods

As I previously stated, I am a massive Rx fan boy, so I was a little disappointed to see that the F# Observable module did not have the full set of extension methods that Rx would have for IObservable<T>. However it seems I am not alone here, and some people have put out a Github project which brings the standard Rx extension methods to F#, here is a link : https://github.com/fsprojects/FSharp.Reactive

F#25 : Active Patterns

Ok so we just wrapped up the final dedicated chunk of the main F# areas, where we looked at OO Programming in F#. These last couple of articles will be miscellaneous ones that I could no really find a home for. This one in particular will be on Active Patterns.

Active pattern allow you to define a pattern that may be used to subdivide the input data, so that you may use regular pattern matching. You can think of active patterns as a way to decompose data in a custom manner to suit your current needs.

You define active patterns using the following sort of syntax

// Complete active pattern definition.
let (|identifer1|identifier2|...|) [ arguments ] = expression
// Partial active pattern definition.
let (|identifier|_|) [ arguments ] = expression

 

You may have one or ore identifiers, and you may have complete or partial active patterns. A complete one will need to match the entire input, whilst a partial one is a partially applied pattern that will match only when applied with the rest of the input data.

We will be examining the difference between complete active patterns and partial active patterns in this post, so have no fear.

 

A Simple Complete Active Pattern Example

Here is a very simple complete active pattern that simply examines an input value, and if the input value is > some threshold, will return one active pattern identifier, otherwise another. The active pattern identifiers are YOUR choice you would pick them to fit your domain.

//A very simple active pattern
let (|DiscountAuthorisationNeeded|DiscountApproved|) input =
    if input > 10 then
        DiscountAuthorisationNeeded else
        DiscountApproved
    

let ApplyDiscount input =
    match input with
    | DiscountAuthorisationNeeded -> printfn "%d : Wil need to be authorised" input
    | DiscountApproved -> printfn "%d : Discount approved" input

ApplyDiscount 7
ApplyDiscount 11
ApplyDiscount 32

Which when run gives the following output:

image

 

Another Complete Active Pattern Example

open System.Drawing

let (|RGB|) (col : System.Drawing.Color) =
    ( col.R, col.G, col.B )

let (|HSB|) (col : System.Drawing.Color) =
    ( col.GetHue(), col.GetSaturation(), col.GetBrightness() )

let printRGB (col: System.Drawing.Color) =
    match col with
    | RGB(r, g, b) -> printfn " Red: %d Green: %d Blue: %d" r g b

let printHSB (col: System.Drawing.Color) =
    match col with
    | HSB(h, s, b) -> printfn " Hue: %f Saturation: %f Brightness: %f" h s b

let printAll col colorString =
    printfn "%s" colorString
    printRGB col
    printHSB col

printAll Color.Red "Red"
printAll Color.Black "Black"
printAll Color.White "White"
printAll Color.Gray "Gray"
printAll Color.BlanchedAlmond "BlanchedAlmond"

Here is another example which I have shamelessly borrowed from MSDN, which shows how you can use active pattern to decompose an input in various different ways. The System.Drawing.Color is an excellent example of this, as it can be expressed in RGB or HSB formats. Here is what this code looks like when it runs:

image

Here is another example that allows you to match against the result of an active pattern

let (|Reversed|) (x:string) = new String(x.Reverse().Cast<char>().ToArray())

let TestActivePattern input = match input with
            | Reversed "rab" -> true
            | _ -> false

printfn "TestActivePattern 'foo'=%A" (TestActivePattern "foo")
printfn "TestActivePattern 'FOO'=%A" (TestActivePattern "FOO")
printfn "TestActivePattern 'bar'=%A" (TestActivePattern "bar")

Which when run gives the following results:

image

Partial Active Patterns

Sometimes what you need is to only match part of the input, luckily F# also allows for this by way of partial active patterns. Partial active patterns do not always produce a result, and as such it is quite common to see them return Option types (Some X, None). To define a partial active pattern, you use a wildcard character (_) at the end of the list of patterns inside the banana clips. This is shown below.

let (|DivisibleBy10|_|) input = if input % 10 = 0 then Some() else None

let printNumberStats x =
    match x with
    | DivisibleBy10  -> printfn "%A is divisible by 10" x
    | _              -> printfn "%A is not divisible by 10" x

[1..20] |> List.iter printNumberStats

Which when run gives the following results:

image

 

Parameterized Active Patterns

Active patterns always take at least one argument for the item being matched, but they may take additional arguments as well, in which case the name parameterized active pattern applies. The canonical example here is to use a regular expression active pattern, which not only takes the regular expression pattern, but also returns the matches. Here is an example of that:

open System.Text.RegularExpressions

let (|RegExGroup|_|) pattern input =
    let m = Regex.Match(input,pattern)
    if (m.Success) then Some m.Groups.[1].Value else None  

let testRegex str =
    match str with
    | RegExGroup "cat" animal ->
            printfn "The value of %s is a cat" animal
    | RegExGroup "dog" animal ->
            printfn "The value of %s is a dog" animal
    | _ -> printfn "The value '%s' is not a beloved pet at all, get another pet hombre" str
   
testRegex "cat"
testRegex "dog"
testRegex "lizard"

Which when run gives the following results:

image

 

NOTE : I hate Regular Expressions, and I once read a post that said if you use Regular Expressions to fix a problem, you now have 2 problems, which I could not agree with more.

F#24 : Reflection

This time we will wrap up the OO leg of our F# journey, by looking into using reflection. Before we start, I just want to point out that some of the examples that I will use here are either modified versions of some examples, or are actual examples by the fabulous Chris Sells, from his amazing “Programming F# 3.0 book”, which I can thoroughly recommend. In the start of that book it states that you are free to use small portions of the code without permission, I considered what I have taken to be a very small portion.

Chris has quite nicely shared all the code from the book on his blog, and it contains some real gems, I would urge you to check it out.

 

General Reflection

NOTE : This is examples in this section and from Chris Sells blog, which I link to at the top of this post

As F# is a member of the .NET family, we are of course to use many of the standard reflection APIs that you have undoubtedly used in your day to day C# lives. However F# also provides extra functions/types and helpers that may be used to deal with F# types. We will look at this F# specific stuff later on within this post.

typeof vs typedefof

F# comes with 2 typexxof operators, typeof<…> and typedefof<..> which are subtly different

  • typeof<..> gives you a runtime representation of a static type
  • typedefof<..> gives a type definition of a static type.

To understand these differences lets see a small example:

printfn "typeof<List<int>> = %A" typeof<List<int>>
printfn "typedefof<List<int>> = %A" typedefof<List<int>>

Which when run will give the following results

image

Defining New Attributes

You have already some examples of attributes usage in F# in some of the previous posts we have done, for example you may have seen these in use

  • [<EntryPoint>]
  • [<AbstractClass>]

These obviously assist the F# compiler, but attributes can be used to do more than this, they can also provide meta data to your own application, and you can reflect on them at run time to see if a type supports certain things/contains certain meta data / control how object are serialized, there are in fact a lot of use cases for attributes. So it should come as no surprise that you should learn how to make your own attributes in F#.

Thankfully this is trivial, we will just build on our new formed OO knowledge and inherit from attribute, and create a new custom attribute.

/// Provide a description for a given class
[<AttributeUsage(AttributeTargets.Class)>]
type ClassDescriptionAttribute(desc) =
    inherit Attribute()
    member this.Description = desc

As you can see this is a new attribute which may only target classes, and will be used to describe a class.

Reflecting On Types

As previously stated, F# is a member of the .NET family so you are free to use any of the types/methods/properties within the standard CLR System.Reflection namespace. One thing you will likely have to do quit often is reflect on a particular type, so lets see an example of that:

// Prints the methods, properties, and fields of a type to the console
let describeType (ty : Type) =
    
    let bindingFlags = 
        BindingFlags.Public   ||| BindingFlags.NonPublic |||
        BindingFlags.Instance ||| BindingFlags.Static    |||
        BindingFlags.DeclaredOnly
    
    let methods = 
        ty.GetMethods(bindingFlags) 
        |> Array.fold (fun desc meth -> desc + sprintf "%s\r\n" meth.Name) ""
       
    let props = 
        ty.GetProperties(bindingFlags)
        |> Array.fold (fun desc prop -> desc + sprintf "%s\r\n" prop.Name) ""

    let fields =
        ty.GetFields(bindingFlags)
        |> Array.fold (fun desc field -> desc + sprintf "%s\r\n" field.Name) ""

    printfn "Name: %s" ty.Name
    printfn "Methods:    \n\t%s\n" methods
    printfn "Properties: \n\t%s\n" props
    printfn "Fields:     \n\t%s" fields

Which you can use like this

let s = new StringWriter()
do describeType(s.GetType()) 

Which when run gives the following results:

image

 

Inspecting Attributes

Inspecting attributes is also very easy (well thanks to Chris Sells blog that). Say we had these types:

/// Provide a description for a given class
[<AttributeUsage(AttributeTargets.Class)>]
type ClassDescriptionAttribute(desc) =
    inherit Attribute()
    member this.Description = desc

/// Provide a description for a given method
[<AttributeUsage(AttributeTargets.Method)>]
type MethodDescriptionAttribute(desc) =
    inherit Attribute()
    member this.Description = desc

type Widget = 
    | RedWidget 
    | GreenWidget
    | BlueWidget

/// XML Doc comments like this one are great for describing a class,
/// but are only available at compile-time. Metadata encoded into
/// attributes is available at run-time.
[<ClassDescription("Represents a stack of Widgets.")>]
type WidgetStack() =

    let mutable m_widgets : Widget list = []

    [<MethodDescription("Pushes a new Widget onto the stack.")>]
    member this.Push(x) = m_widgets <- x :: m_widgets

 

We can easily inspect the attributes and get their values using the following code (again thanks Chris Sells):

/// Displays data attributed with the MethodDesc or ClassDesc attributes
let printDocumentation(ty : Type) =

    // Return if a object has a given type
    let objHasType ty obj = (obj.GetType() = ty)

    let classDescription : string option = 
        ty.GetCustomAttributes(false)
        |> Seq.tryFind(objHasType typeof<ClassDescriptionAttribute>)
        |> Option.map(fun attr -> (attr :?> ClassDescriptionAttribute))
        |> Option.map(fun cda -> cda.Description)
    
    let methodDescriptions : seq<string * string option> =
        ty.GetMethods()
        |> Seq.map(fun mi -> mi, mi.GetCustomAttributes(false))
        |> Seq.map(fun (methodInfo, methodAttributes) ->
            let attributeDescription =
                methodAttributes
                |> Seq.tryFind(objHasType typeof<MethodDescriptionAttribute>)
                |> Option.map(fun atr -> (atr :?> MethodDescriptionAttribute))
                |> Option.map(fun mda -> mda.Description)
            methodInfo.Name, attributeDescription)
    
    let getDescription = function
                            | Some(desc) -> desc
                            | None       -> "(no description provided)"
    
    printfn "Info for class: %s" ty.Name
    printfn "Class Description:\n\t%s" (getDescription classDescription)
    printfn "Method Descriptions:"
    
    methodDescriptions 
    |> Seq.iter(fun (methName, desc) -> 
        printfn "\t%15s - %s" methName (getDescription desc))

Which when run with this demo code, will produce the output shown below

image

 

 

 

Properties, Get A Value, Set A Value

To get and set a property value is also trivial, we can just get a property using the standard System.Reflection namespace and then use the GetValue(..) and SetValue(..) methods exposed by the CLR.

I kind of feel a bit guilty using so many of Chris’s bit of code, but it is just so good, and highly enlightening. For example what is shown below, is very cool in that it shows how to create a new property get/set operator which behind the scenes uses reflection:

// Type for representing a book
type Book(title, author) =
    // Current page, if the book is opened
    let mutable m_currentPage : int option = None

    member this.Title  = title
    member this.Author = author
    member this.CurrentPage with get () = m_currentPage
                            and  set x  = m_currentPage <- x

    override this.ToString() =
        match m_currentPage with
        | Some(pg) -> sprintf "%s by %s, opened to page %d" title author pg
        | None     -> sprintf "%s by %s, not currently opened" title author

// CREATE SOME CUSTOM OPERATORS, WHICH IS AS EASY AS CREATING SOME FUNCTIONS
// IN F#

// Get a property value. Notice that the return type is generic.
let (?) (thingey : obj) (propName: string) : 'a =
    let propInfo = thingey.GetType().GetProperty(propName)
    propInfo.GetValue(thingey, null) :?> 'a

// Set a property value.
let (?<-) (thingey : obj) (propName : string) (newValue : 'a) =
    let propInfo = thingey.GetType().GetProperty(propName)
    propInfo.SetValue(thingey, newValue, null)

 

Which we can use as follows, take note of the “?” operators in action (which are really just functions, thus is the awesomeness of F#):

let book = new Book("Foundation", "Asimov")


printfn "%A" book.CurrentPage
book?CurrentPage <- Some(14)
printfn "%A" book.CurrentPage
let currentPage : int option = book?CurrentPage
printfn "%A" currentPage

book?CurrentPage <- Some(24)
printfn "%A" book.CurrentPage
let currentPage : int option = book?CurrentPage
printfn "%A" currentPage

Which when run gives us the following results:

image

 

 

F# Specific Reflection

What we have discussed so far has been how to leverage the existing .NET reflection namespace, which is totally fine, but what does F# have to offer us by way of reflection APIs.

F# actually offers a few modules to help with reflection of F# types. Lets have a brief look at these modules

Reflection.FSharpType

Contains operations associated with constructing and analyzing F# types such as records, unions and tuples. You can read more about this module here: http://msdn.microsoft.com/en-us/library/ee370530.aspx

Here is what is available within this module:

image

Here are some examples of this module

open Microsoft.FSharp.Reflection

type ContactCard = 
    {   Name     : string;
        Phone    : string; }

/// Represents the suit of a playing card
type Suit = 
    | Hearts 
    | Clubs 
    | Diamonds 
    | Spades

/// Represents the rank of a playing card
type Rank = 
    /// Represents the rank of cards 2 .. 10
    | Value of int
    | Ace
    | King
    | Queen
    | Jack
....
....
let aTuple = (12,13)
let aFunction() =
    printfn "Im function"
let aRecord = { Name = "Alf" ; Phone = "(206) 555-0157" ;  }
let aDiscrimatingUnion1 = Value(3)
let aDiscrimatingUnion2 = Rank.Ace



printfn "aTuple IsTuple = %A" (FSharpType.IsTuple(aTuple.GetType()))
printfn "aFunction IsTuple = %A" (FSharpType.IsTuple(aFunction.GetType()))

printfn "aTuple IsFunction = %A" (FSharpType.IsFunction(aTuple.GetType()))
printfn "aFunction IsFunction = %A" (FSharpType.IsFunction(aFunction.GetType()))

printfn "aRecord IsRecord = %A" (FSharpType.IsRecord(aRecord.GetType()))
 
printfn "aDiscrimatingUnion1 IsUnion = %A" (FSharpType.IsUnion(aDiscrimatingUnion1.GetType()))
printfn "aDiscrimatingUnion2 IsUnion = %A" (FSharpType.IsUnion(aDiscrimatingUnion2.GetType()))

Which when run will give the following output

image

Reflection.FSharpValue

Contains operations associated with constructing and analyzing values associated with F# types such as records, unions and tuples. You can read more about this module here: http://msdn.microsoft.com/en-us/library/ee353505.aspx

Here is what is available within this module:

image

Here are some examples of this module

open Microsoft.FSharp.Reflection
open System.Reflection

type ContactCard = 
    {   Name     : string;
        Phone    : string; }

/// Represents the suit of a playing card
type Suit = 
    | Hearts 
    | Clubs 
    | Diamonds 
    | Spades

/// Represents the rank of a playing card
type Rank = 
    /// Represents the rank of cards 2 .. 10
    | Value of int
    | Ace
    | King
    | Queen
    | Jack

....
....

let aRecord = { Name = "Alf" ; Phone = "(206) 555-0157" ;  }
let aDiscrimatingUnion1 = Value(3)
let aDiscrimatingUnion2 = Rank.Ace

printfn "GetRecordFields(aRecord, BindingFlags.Public) = %A" 
    (FSharpValue.GetRecordFields(aRecord, BindingFlags.Public))
printfn "GetUnionFields(aDiscrimatingUnion1, aDiscrimatingUnion2.GetType()) = %A" 
    (FSharpValue.GetUnionFields(aDiscrimatingUnion1, aDiscrimatingUnion2.GetType()))
printfn "GetUnionFields(aDiscrimatingUnion2, aDiscrimatingUnion2.GetType()) = %A" 
    (FSharpValue.GetUnionFields(aDiscrimatingUnion2, aDiscrimatingUnion2.GetType()))

Which when run gives the following results

image

 

Reflection.UnionCaseInfo

Represents a case of a discriminated union type. You can read more about this module here: http://msdn.microsoft.com/en-us/library/ee370473.aspx

Here is what is available within this module:

image

F#23 : Generics

So we are about 1/2 way through the OO segment of our F# journey, we just have this article and one other to do. This one will focus on generics support in F#, we shall be covering the following topics

  • Implicit Generics
  • Explicit Generics
  • Using Generics In Various Types
  • Generic Constraints

I should just point out that I will not have time (or the will power) to go through all the generic constraints that F# supports, but I will try my best to show the basics.

So without further ado, shall we get on with the post at hand

 

Implicit Generics

In F# the type inference system is so good that some of the time you will not even need to tell the type system that an argument is generic. Essentially where ever the F# type system can treat a function as generic it will do so. Consider the following 2 examples that I have typed into the FSI window

let someFunction(x) = x
let makeList a b = [a; b]

If we examine these 2 functions in the FSI window, this is what we would get for the 2 functions above:

val makeList : a:’a -> b:’a -> ‘a list

val someFunction : x:’a -> ‘a

It can be seen that although I did not actually ask for he arguments to be generic they were inferred to be generic ones. You can of course implicitly say that you wish a certain parameter to be generic, which is done using the single quotation syntax which is typically “’a” to show that a type is expected to be a generic one.

Here are those to functions rewritten to expect generic parameters:

let someFunction(x : 'a) = x
let makeList (a : 'a) (b : 'a) = [a; b]


do printfn "%A" (someFunction 12)
do printfn "%A" (someFunction "cat")

do printfn "%A" (makeList 1 2)
do printfn "%A" (makeList "cat" "dog")

It can be seen that I am now able to use the 2 demo functions to accept Ints, or Strings. Here is what it looks like when I run the above code:

image

Explicit Generics

It is also possible to create explicit generic functions/types. This is done using the angle bracket syntax “<T>”, which would undoubtedly be familiar to any C# developers reading this. Here is are the 2 previous examples rewritten to use explicit generics. I have also included a 3rd function which expects 2 generic parameters which are simply printed to the console.

let someFunction (x : 'a) = x
let makeList (a:'a) (b:'a) = [a; b]
let printGenerics (x:'a) (y:'b) = 
    printfn "x = %A, y = %A" x y
        

It can now be seen if we try and use this these functions with a particular generic type specified in the generic type “<T>” but supply some other type, we will get a compilation error:

image 

If we however play nice, and pass in the correct types expected, we do indeed get the correct results:

do printfn "%A" (someFunction 12)
do printfn "%A" (someFunction "cat")

do printfn "%A" (makeList 1 2)
do printfn "%A" (makeList "cat" "dog")

printGenerics 1 2
printGenerics 1 "cat"

Which gives the following results:

image

Using Generics In Various Types

I mentioned earlier that you can also use generics in other types such as records, and  unions. Here are some very trivial examples of how you could declare record and unions that are generic:

// A generic record, with the type parameter in angle brackets. 
type GenericRecord = 
    {
        Field1: 'a;
        Field2: 'a;
    }

// A generic discriminated union. 
type GenericUnion =
    | Choice1 of 'a
    | Choice2 of 'a * 'a

 

And here are some examples usages of these:

let rec1 =  { Field1 = "ABC" ; Field2 = "XYZ" }
let rec2 =  { Field1 = 12 ; Field2 = 45 }


let genericUnion1 = Choice1(12)
let genericUnion2 = Choice1(4343.0)
let genericUnion3 = Choice1("122.33")
let genericUnion4 = Choice2(12, 15)
let genericUnion5 = Choice2(2.0, 4.0)
let genericUnion6 = Choice2("1","2") 

Which when run gives the following output

image

Generic Constraints

We now move on to look at generic constraints in F#. Generic constraints are used when you work with generic types to limit what may be allowed as generic type. Constraints may sometimes be required, as without them the compiler would have no way of verifying the features that are available on the generic type until runtime.

Most commonly this would be to say that the generic type inherits from a certain base class or implements a certain interface, but in F# there is a very good generic constraint system that allows us to constraint quite a few things.

I have shamelessly stolen this table and the matching generic constraints from  MSDN : http://msdn.microsoft.com/en-us/library/dd233203.aspx

image

As you can see there is quite a lot you can do with generic constraints in F#. Let’s now see what this looks like when used in some actual code:

//Dummy class to be used in some of the 
type Foo() =
    class end

//Dummy class to be used in some of the 
type Dimension =
    struct 
        val Width: float
        val Height: float
        new(w: float, h: float) = { Width = w; Height = h}
    end


type MyNotSoUsefulException() =
    inherit Exception()
            
// Base Type Constraint
type Class1 System.Exception> =
        val ex : 'T
        new(e : 'T) = { ex = e}


// Reference type constraint
type Class2 =
        val refField : 'T
        new(r : 'T) = { refField = r}

// Interface Type Constraint
type Class3 System.IComparable> = 
    class end

// Null constraint
type Class4 =
    class end

// Member constraint with static member
type Class5 'T) > =
    class end

// Member constraint with instance member
type Class6 int)> =
    class end

// Member constraint with property
type Class7 =
    class end

// Constructor constraint
type Class8 'T)>() =
    member val Field = new 'T()

// Enumeration constraint with underlying value specified
type Class9<'T when 'T : enum> =
    class end

// 'T must implement IComparable, or be an array type with comparable
// elements, or be System.IntPtr or System.UIntPtr. Also, 'T must not have
// the NoComparison attribute.
type Class10 =
    class end

// 'T must support equality. This is true for any type that does not
// have the NoEquality attribute.
type Class11 =
    class end

type Class12<'T when 'T : delegate> =
    class end

type Class13 =
    class end
    
// If there are multiple constraints, use the and keyword to separate them.
type Class14 =
    class end

// Member constraints with two type parameters
// Most often used with static type parameters in inline functions
let inline add(value1 : ^T when ^T : (static member (+) : ^T * ^T -> ^T), value2: ^T) =
    value1 + value2

// ^T and ^U must support operator +
let inline heterogenousAdd(value1 : ^T when (^T or ^U) : (static member (+) : ^T * ^U -> ^T), value2 : ^U) =
    value1 + value2



Lets have a look at one or 2 of them.

Class 1

Class 1 from the list above should only be able to accept Exception derived classes. Here is the full code for it

type MyNotSoUsefulException() =
    inherit Exception()
            
// Base Type Constraint
type Class1 System.Exception> =
        val ex : 'T
        new(e : 'T) = { ex = e}

Which as we can see will not compile if we try and use a non Exception derived type, but will compile if we do

image

Class 2

Class 2 from the list above should only be able to reference types, no structs should be allowed. Here is the full code for it


//Dummy class to be used for demos
type Foo() =
    class end

//Dummy class to be used for demos
type Dimension =
    struct 
        val Width: float
        val Height: float
        new(w: float, h: float) = { Width = w; Height = h}
    end

// Reference type constraint
type Class2 =
        val refField : 'T
        new(r : 'T) = { refField = r}

Which as we can see will not compile if we try and use a non reference type, but will compile if we do

image

 

The other generic constraints all work in the same manner, you can have fun and try the others on your own

F#22 : Abstract classes / Overriding Methods / Implementing Interfaces

In this article we continue the OO leg of our F# journey. So this time we will look at abstract classes / overriding methods and how to implement interfaces

 

Abstract Methods / Virtual Method

F# like the rest of the .NET languages allow you to mark a method (function) as abstract. There is a subtle difference in that you must declare a member as abstract even you do not supply a default implementation. You can kind of think as abstract methods with no default implementation as a abstract method, and a abstract member with a default implementation as a virtual member. There is no virtual keyword in F#.

In order to have a pure abstract method (that is one with no default implementation) you need to use the special AbstractClass attribute, otherwise you will get a compile time error

 

image

Let’s ignore this for now and concentrate on some working code:

 

Virtual Methods

Here is  an example of an abstract method that has a default implementation(which is achieved using the default keyword), which is the equivalent of a virtual method in C#, here is an example of this:


type SomeBaseClass() =
    let mutable z = 0
    abstract member SomeVirtualMethod : int -> int
    default this.SomeVirtualMethod(a : int) = 
        z <- z + a 
        z

type SomeDerivedClass() =
    inherit SomeBaseClass()
    override this.SomeVirtualMethod(a: int) = a * 2

It can be seen that in the SomeDerived class we can override the base implementation by using the override keyword, which works much the same as it does in any other .NET languages, you are selectively choosing to provide a new implementation for the method you are overriding. What is quite different in F# is that you lack some of the finer points of say C#, such as

  • Using the “new” keyword to hide an implementation of  a particular method
  • Calling into the original base class method in an overridden method

Here is an example of a virtual method in use:

let foo = new SomeDerivedClass()
printfn "foo.SomeVirtualMethod(24) %A" (foo.SomeVirtualMethod(24))
 

Which when run gives this result

image

 

Abstract Methods

So we just talked about the F# equivalent of “virtual” members, which were ones that are abstract but also supplied a default implementation. But what about abstract members that do not supply a default implementation, how do we deal with those. Here is a small example of that, this time we have to use the AbstractClass attribute, to denote that the whole class is abstract. This allows the definition of a type with abstract members that do not have any implementation, were the actual implementation will be supplied by the inheritor of the abstract class.

[<AbstractClass>]
type SomeBaseClass() =
    abstract member SomeAbstractMethod : int -> unit
        
type SomeDerivedClass() =
    inherit SomeBaseClass()
    override this.SomeAbstractMethod(a: int) = printfn "a was %A" a |> ignore

Here is an example of a abstract class/method in use:

let foo = new SomeDerivedClass()
printfn "foo.SomeAbstractMethod(24)" |> ignore
do foo.SomeAbstractMethod(24)

Which when run gives this result

image

 

Calling Base Class Constructors

The constructor for the base class must be called in the derived class.The arguments for the base class constructor appear in the argument list in the inherit clause. This is achievable in F# though it is certainly not as pretty as it is in C# say. We have already seen the case when there is a simple no parameter constructor, but what about the cases when the base type contains a constructor that contains parameters or maybe even has several constructors, how do we deal with that. I think the best way to show how to deal with that is by way of an example. So here is an example where we have a base type that has a mixture of constructors, and is then inherited from.

type SomeBaseClass =
    val stringField : string
    new (s) = { stringField = s }
    new () = { stringField = "" }

type DerivedClass =
    inherit SomeBaseClass
    val stringField2 : string
    new (s1, s2) = { inherit SomeBaseClass(s1); stringField2 = s2 }
    new (s2) = { inherit SomeBaseClass(); stringField2 = s2 }
    new () = { inherit SomeBaseClass(); stringField2 = "" }

As you can see there is little bit more ceremony to deal with here, such as the braces “{}” and the extra use of the inherit keyword wherever you need to call a base class constructor. That said once you get used to it, I don’t think it is that bad.

Object Expressions

Sometimes you may only need to do a minor change, in which case F# offers an alternative approach to inheritance, by way of a technique called “Object Expressions”. Here is a trivial example of this:

 

let public myObjectExpressionObject = 
        { 
        new Object() with 
            override this.ToString() = "Override the object.ToString() method"
        }

It can be seen all we wanted to do was supply a new ToString() method for our usage but we did not inherit from anything at all, in fact there is no custom type at all there, just a let binding and an object expression where we override the ToString() method of the object type.

Which we can use like this:

let result = myObjectExpressionObject.ToString()
printfn "myObjectExpressionObject.ToString() = %A" result

Which will give the expected result of:

image

 

Implementing Interfaces / Calling Interface Methods

To define an interface you simply declare  a type with abstract members. To implement an interface you simply use the interface XXX with syntax, and then provide the members details for the original members of the interface. Here is a small example.

type IOrderDetails =
    abstract member Describe : unit -> string

type Order(x: int, y: string, z: DateTime) =
    interface IOrderDetails with 
        member this.Describe() = String.Format("{0} : {1} x {2}",  z.ToShortTimeString(), x, y)
  • This declares a very simple interface called IOrderDetails that has a single member
  • We then provide a custom Order type that implements the IOrderDetails interface

So that is how you declare an interface, but as some point you will want to be able to call the interface methods that you have implemented, so how do you do that?

If i create a new Order object and look at the intellisense it can be seen that the IOrderDetails.Describe member is not listed there:

image

mmmmm perhaps some sort of cast is required to cast the Order instance to the IOrderDetails interface that it implements. Yes this is the correct answer. In C# you have 2 choices here, you can use the cast operator ((IOrderDetails)o).Describe() or you may use the as keyword which can be used like this (o as IOrderDetails).Describe(). We are however not using C# and are using F, so we need to focus on what we need to do in F#.

The idea is the same though, we need to cast. Here is the working code for the example IOrderDetails interface implementation:

let o = new Order(1, "Star Wars DVD", DateTime.Now) 
printfn "((o :> IOrderDetails).Describe()) = %A" ((o :> IOrderDetails).Describe())

Which when run gives the following (expected) results:

image

F# 21 : Events

We continue our OO journey, and this time we look at events within classes.

Events are a good way for no related classes t communicate, you can think of events as a kind of publish-subscribe arrangement, where the source of the event (the class that contains the event) is the publisher, whilst a consumer of the event is the subscriber.

According to MSDN (http://msdn.microsoft.com/en-us/library/dd233189.aspx)

F# events are represented by the F# Event class, which implements the IEvent interface. IEvent is itself an interface that combines the functionality of two other interfaces, IObservable<T> and IDelegateEvent. Therefore, Events have the equivalent functionality of delegates in other languages, plus the additional functionality from IObservable, which means that F# events support event filtering and using F# first-class functions and lambda expressions as event handlers.

This is actually pretty cool, as we can use the full gamut of Observable functions with F# events straight out of the box

Adding Events To A Class

Here is some code that shows how to add custom events to a custom class. There are several key points here:

  • We need to declare a private let binding which may or may not be a generic new Event type  (depending on how you want your event to work more on this later)
  • We need to use a CLIEvent attribute on the member itself. This instructs the compiler to emit a CLR type event signature with the standard Add/Remove event handler methods
  • We need to use the .Publish from the private event value when exposing the member
  • We can raise the event using the Trigger(..) function of the private event. The Trigger function call will need to match the type of the Event arguments you chose to use, if you chose to let it be anything using the “Event<_>”, then it should take the form of this, args, which is the sender(ie this class), and the event args you want to use
type MyCustomEventArgs<'a>(value : string) =
    inherit System.EventArgs()

    member this.Value = value

type MyCustomDelegate<'a> = delegate of obj * MyCustomEventArgs<'a> -> unit

type MyClassWithCLIEvent<'a when 'a : comparison>() =

    let customEventArgsEvent = new Event<string>()
    let genericEventArgsEvent = new Event<_>()
    let standardDotNetEventArgsEvent = new Event<EventHandler, EventArgs>()
    let customEventHandlerEvent = new Event<MyCustomDelegate<string>, MyCustomEventArgs<string>>()

    [<CLIEvent>]
    member this.CustomEventArgsEvent = customEventArgsEvent.Publish

    [<CLIEvent>]
    member this.GenericEventArgsEvent = genericEventArgsEvent.Publish

    [<CLIEvent>]
    member this.StandardDotNetEventArgsEvent = standardDotNetEventArgsEvent.Publish

    [<CLIEvent>]
    member this.CustomEventHandlerEvent = customEventHandlerEvent.Publish

    member this.TestCustomEventArgsEvent(arg : string) =
        customEventArgsEvent.Trigger(arg)

    member this.TestGenericEventArgsEvent(args : string) =
        genericEventArgsEvent.Trigger(this, args)

    member this.TestStandardDotNetEventArgsEvent() =
        standardDotNetEventArgsEvent.Trigger(this, EventArgs.Empty)

    member this.TestCustomEventHandlerEvent(x) =
        customEventHandlerEvent.Trigger(this, new MyCustomEventArgs<_>(x))

Raising Events

We just saw this above where we use the Trigger(..) function of the Event that is being exposed. This would tyically be done is a function that could be  used internally, though you may want to expose the facility to raise the event outside the class that has the event, but in my opinion that would should be quite a rare case.

 

Subscribing To Events

Suppose we had this VERY simple win forms F# application with this code. This code actually shows you how to subscribe to 2 exists events, namely

  • Form.MouseMove : Which expects to have a event handler which takes System.Windows.Forms.MouseEventArgs, so in the handler we setup we make sure that the event arguments are just that.
  • Form.Click : Which expects to have System.EventArgs

When subscribing to events you have 2 choices:

  1. You may use the Add which has the following signature callback: (’T –> unit) –> unit
  2. You may also use the AddHandler

It is really just a question of creating your correct event handlers and then Adding them to the events invocation list using the Add(..) function

open System.Windows.Forms

[<EntryPoint>]
let main argv = 

    let ShowMessageOnClickHandler evArgs =
        MessageBox.Show("Clicked") |> ignore

    let form = new Form(Text = "F# Windows Form",
                        Visible = true,
                        TopMost = true)

    let MouseMoveEventHandler (evArgs : System.Windows.Forms.MouseEventArgs) =
        form.Text <- System.String.Format("{0},{1}", evArgs.X, evArgs.Y)

    //adds the Click handler delegate (function in F#)
    form.Click.Add(ShowMessageOnClickHandler)

    //adds the MouseMove handler delegate (function in F#)
    form.MouseMove.Add(MouseMoveEventHandler)
    Application.Run(form)

    0

If you run this code, and click anywhere on the form you will get a MessageBox shown

image

Lets revisit our custom class that had it own events where we had this code:

type MyCustomEventArgs<'a>(value : string) =
    inherit System.EventArgs()

    member this.Value = value

type MyCustomDelegate<'a> = delegate of obj * MyCustomEventArgs<'a> -> unit

type MyClassWithCLIEvent<'a when 'a : comparison>() =

    let customEventArgsEvent = new Event<string>()
    let genericEventArgsEvent = new Event<_>()
    let standardDotNetEventArgsEvent = new Event<EventHandler, EventArgs>()
    let customEventHandlerEvent = new Event<MyCustomDelegate<string>, MyCustomEventArgs<string>>()

    [<CLIEvent>]
    member this.CustomEventArgsEvent = customEventArgsEvent.Publish

    [<CLIEvent>]
    member this.GenericEventArgsEvent = genericEventArgsEvent.Publish

    [<CLIEvent>]
    member this.StandardDotNetEventArgsEvent = standardDotNetEventArgsEvent.Publish

    [<CLIEvent>]
    member this.CustomEventHandlerEvent = customEventHandlerEvent.Publish

    member this.TestCustomEventArgsEvent(arg : string) =
        customEventArgsEvent.Trigger(arg)

    member this.TestGenericEventArgsEvent(args : string) =
        genericEventArgsEvent.Trigger(this, args)

    member this.TestStandardDotNetEventArgsEvent() =
        standardDotNetEventArgsEvent.Trigger(this, EventArgs.Empty)

    member this.TestCustomEventHandlerEvent(x) =
        customEventHandlerEvent.Trigger(this, new MyCustomEventArgs<_>(x))

When you declare your Event<’T>, one of the things you need to decide is what type of event handler you want to expose/allow users to use, this will dictate what type of Event<’T> you will declare. The above code demonstrates 3 possible flavours of Event<’T>, which are:

  1. Custom event argument type
  2. Generic event arguments
  3. Standard Handler/EventArgs which will be of the type sender EventArgs (this is the standard in .NET), you could obviously use any EventHandler and EventArgs you like
  4. Custom EventHandler delegate and EventArgs

Custom EventArgs

As can be seen from the code that when we choose to use a custom object type for the event we end up with this sort of code in the event source class

type MyClassWithCLIEvent<'a when 'a : comparison>() =

    let customEventArgsEvent = new Event<string>()

    [<CLIEvent>]
    member this.CustomEventArgsEvent = customEventArgsEvent.Publish

    member this.TestCustomEventArgsEvent(arg : string) =
        customEventArgsEvent.Trigger(arg)

Where we can subscribe using this sort of code when subscribing

    let classWithEvent = new MyClassWithCLIEvent<string>()

    let handler = new Handler<string>(fun sender args -> printfn "CustomEventArgsEvent AddHandler with new Handler<string> : %s" args)
    classWithEvent.CustomEventArgsEvent.AddHandler(handler)

    classWithEvent.TestCustomEventArgsEvent("I Am TestCustomEventArgsEvent")
    classWithEvent.TestCustomEventArgsEvent("I Am TestCustomEventArgsEvent")
    classWithEvent.TestCustomEventArgsEvent("I Am TestCustomEventArgsEvent")

    //removing handler for CustomEventArgsEvent, so it should not fire any more
    classWithEvent.CustomEventArgsEvent.RemoveHandler(handler)
    classWithEvent.TestCustomEventArgsEvent("I Am event1")
    classWithEvent.TestCustomEventArgsEvent("I Am event1")
    classWithEvent.TestCustomEventArgsEvent("I Am event1")

Generic Event Arguments

As can be seen from the code that when we choose to use a generic Event<..> we end up with this sort of code in the event source class

type MyClassWithCLIEvent<'a when 'a : comparison>() =

    let genericEventArgsEvent = new Event<_>()

    [<CLIEvent>]
    member this.GenericEventArgsEvent = genericEventArgsEvent.Publish

    member this.TestGenericEventArgsEvent(args : string) =
        genericEventArgsEvent.Trigger(this, args)

As can be seen from the code that when we choose to use a generic Event<..> type for the event we end up with this sort of code in the event source class, where we must use sender args when we subscribe. We need to match the args with the correct type when we raise the event as the raising method expects a string value in this example

    let classWithEvent = new MyClassWithCLIEvent<string>()

    classWithEvent.GenericEventArgsEvent.Add(fun (sender, arg) ->
            printfn "Event1 occurred! Object data: %s" arg)

    classWithEvent.TestGenericEventArgsEvent("I Am TestGenericEventArgsEvent")

Using Standard EventHandler/EventArgs

As can be seen from the code that when we choose to use a generic Event<EventHandler/EventArgs> we end up with this sort of code in the event source class

type MyClassWithCLIEvent<'a when 'a : comparison>() = 

    let standardDotNetEventArgsEvent = new Event<EventHandler, EventArgs>() 

    [<CLIEvent>]
    member this.StandardDotNetEventArgsEvent = standardDotNetEventArgsEvent.Publish

    member this.TestStandardDotNetEventArgsEvent() =
        standardDotNetEventArgsEvent.Trigger(this, EventArgs.Empty)

As can be seen from the code that when we choose to use a generic Event<EventHandler/EventArgs> type for the event we need to create a new EventHandler when we subscribe

    let classWithEvent = new MyClassWithCLIEvent<string>()

    classWithEvent.StandardDotNetEventArgsEvent.AddHandler(
        EventHandler(fun _ _ -> printfn "StandardDotNetEventArgsEvent.AddHandler"))

    classWithEvent.TestStandardDotNetEventArgsEvent()
    classWithEvent.TestStandardDotNetEventArgsEvent()

Using Custom Delegate And Custom EventArgs

We can also create our own custom EventHandler delegate and create completely custom EventArgs, this is shown below:

type MyClassWithCLIEvent<'a when 'a : comparison>() =

    let customEventHandlerEvent = new Event<MyCustomDelegate<string>, MyCustomEventArgs<string>>()

    [<CLIEvent>]
    member this.CustomEventHandlerEvent = customEventHandlerEvent.Publish

    member this.TestCustomEventHandlerEvent(x) =
        customEventHandlerEvent.Trigger(this, new MyCustomEventArgs<_>(x))

As can be seen from the code that when we choose to use a custom EventHandler delegate, we need to use an instance of the custom EventHandler delegate when we subscribe

    let classWithEvent = new MyClassWithCLIEvent<string>()

    let delegateHandler = new MyCustomDelegate<string>(fun sender args -> printfn "CustomEventArgsEvent AddHandler new MyCustomDelegate<string> : %s" args.Value)
    classWithEvent.CustomEventHandlerEvent.AddHandler(delegateHandler)

    classWithEvent.TestCustomEventHandlerEvent("I Am TestCustomEventHandlerEvent")

If you use events you will undoubtedly know about the problem where the subscriber may outlive the source of an event, and if we do not unhook an event handler we will get a memory leak, so it will come as no surprise that we are also able to Remove events subscriptions using RemoveHandler.

Here is the full demo code:

let classWithEvent = new MyClassWithCLIEvent<string>()

let handler = new Handler<string>(fun sender args -> printfn "CustomEventArgsEvent AddHandler with new Handler<string> : %s" args)
classWithEvent.CustomEventArgsEvent.AddHandler(handler)

classWithEvent.GenericEventArgsEvent.Add(fun (sender, arg) ->
        printfn "Event1 occurred! Object data: %s" arg)

classWithEvent.StandardDotNetEventArgsEvent.AddHandler(
    EventHandler(fun _ _ -> printfn "StandardDotNetEventArgsEvent.AddHandler"))

let delegateHandler = new MyCustomDelegate<string>(fun sender args -> printfn "CustomEventArgsEvent AddHandler new MyCustomDelegate<string> : %s" args.Value)
classWithEvent.CustomEventHandlerEvent.AddHandler(delegateHandler)

classWithEvent.TestCustomEventArgsEvent("I Am TestCustomEventArgsEvent")
classWithEvent.TestCustomEventArgsEvent("I Am TestCustomEventArgsEvent")
classWithEvent.TestCustomEventArgsEvent("I Am TestCustomEventArgsEvent")
classWithEvent.TestGenericEventArgsEvent("I Am TestGenericEventArgsEvent")
classWithEvent.TestStandardDotNetEventArgsEvent()
classWithEvent.TestStandardDotNetEventArgsEvent()
classWithEvent.TestCustomEventHandlerEvent("I Am TestCustomEventHandlerEvent")

//removing handler for CustomEventArgsEvent, so it should not fire any more
classWithEvent.CustomEventArgsEvent.RemoveHandler(handler)
classWithEvent.TestCustomEventArgsEvent("I Am event1")
classWithEvent.TestCustomEventArgsEvent("I Am event1")
classWithEvent.TestCustomEventArgsEvent("I Am event1")

Which shows adding event subscriptions, and removing them too.

This produces the following output:

image

Implementing Interfaces That Contain Events

Occasionally you will get an interface or abstract class that has an event on it, and you need to implement the event in your type. A canonical example is the System.ComponentModel.INotifyPropertyChanged interface, which has the following attributes:

  1. Single PropertyChanged event
  2. PropertyChangedEventHandler delegate
  3. PropertyChangedEventArgs

 

So to implement this in your own code, you would simply do something like this:

open System
open System.Collections.Generic
open System.ComponentModel

type INPCObject() =
    let mutable total = 0.0
    let mutable name = ""

    let propertyChanged = Event<_, _>()
    interface INotifyPropertyChanged with
        [<CLIEvent>]
        member x.PropertyChanged = propertyChanged.Publish

    member this.Total
        with get() = total
        and  set(v) =
            total <- v
            propertyChanged.Trigger(this, new PropertyChangedEventArgs("Total"))

    member this.Name
        with get() = name
        and  set(v) =
            name <- v
            propertyChanged.Trigger(this, new PropertyChangedEventArgs("Name"))

Where you would hook up a subscription to this event, like this:

open System.ComponentModel
.....
.....
let classWithEvent = new INPCObject()

let inpc = (classWithEvent :> INotifyPropertyChanged)
inpc.PropertyChanged.AddHandler(
    (fun sender args -> printfn "PropertyChanged was : %s " args.PropertyName))

classWithEvent.Total <- 23.6;
classWithEvent.Name <- "yo";
classWithEvent.Total <- 11.2;

Which when run will give the following results:

image

MailBoxProcessor

Although not directly related to the subject at hand, I just want to mention a rather cool F# class called “MailBoxProcessor”, which is a message processing agent. It is quite cool, and could be used to send messages between objects with a little bit of love (think Mediator pattern here hint hint)

Here is a link to the class, have a read : http://msdn.microsoft.com/en-us/library/ee370357.aspx

 

Weak Events / Observable Module

Although slightly off topic for this brief introduction into F#, I thought it may be useful to point out some further resources that may help when working with events in general as well as Rx:

Further Reading I

Lovely Weak Event Article

This is a very in depth article about weak events, and presents several solutions to the problem, though the demos are in C#, it is still an excellent read, and one that everyone should read

Further Reading II

Paul Stovells Weak Event Proxy

A simple easy to use proxy to allow event subscription to be made weakly, which allows event source to be garbage collected even if a subscriber outlives the source life time.

I actually found a bit of time today to have a stab at translating Pauls Weak Event proxy into F#, which is shown below. Now this is not a generic version which Pauls original post was, but it was done with the purpose of demonstrating how to handle weak events, so if any of you want a generic version that is capable of dealing with any EventHandler delegate and EventArgs derived class it should not be that hard to change.

So here is the code, the crucial bit t note is that we hook the original source event up to a weak event (thanks to WeakReference) proxy, which will only raise the event if the event source is still alive. More crucially because we use a WeakReference we allow the original source object to be garbage collected, which is demonstrated when we set it to a default value and attempt to change one of its properties before we assign a new event source object.

Anyway enough waffle here is the code for the relevant types:

open System
open System.Diagnostics
open System.ComponentModel

//WeakPropertyChangedEventHandler for PropertyChangedEventHandler
[<DebuggerNonUserCode>]
type public WeakPropertyChangedEventHandler(callback : PropertyChangedEventHandler) =
    let _method = callback.Method
    let _targetReference  = new WeakReference(callback.Target, true);

    [<DebuggerNonUserCode>]
    member public this.Handler(sender, e : PropertyChangedEventArgs) =
        let target = _targetReference.Target;
        if (target <> null) then
            let callback = Delegate.CreateDelegate(typedefof<PropertyChangedEventHandler>, target, _method, true) :?> PropertyChangedEventHandler
            if (callback <> null) then
                callback.Invoke(sender, e);
            ()
        else
            ()

//Event Consumer
type SomeClassWithStoredEventObject(inpcObject) as this =
    let mutable eventSourceObject = inpcObject
    do this.HookEvent()

    member this.HookEvent() =
        let inpc = eventSourceObject :> INotifyPropertyChanged
        let inpcHandler = new PropertyChangedEventHandler(
            fun obj args -> printfn "Property Changed!")
        let WeakPropertyChangedEventHandler = new WeakPropertyChangedEventHandler(inpcHandler)
        let weakInpcHandler = new PropertyChangedEventHandler(
            fun obj args -> WeakPropertyChangedEventHandler.Handler(obj, args))
        do inpc.PropertyChanged.AddHandler(weakInpcHandler) |> ignore

    member this.EventSourceObject
        with get() = eventSourceObject
        and set(v) =
            eventSourceObject <- v
            this.HookEvent()

//Event producer
type INPCObject() =
    let mutable age = 0.0

    let propertyChanged = Event<_,_>()
    interface INotifyPropertyChanged with
        [<CLIEvent>]
        member x.PropertyChanged = propertyChanged.Publish

    member this.Age
        with get() = age
        and set(v) =
            age <- v
            propertyChanged.Trigger(this, new PropertyChangedEventArgs("Age"))

 

Where we have this consuming code:

let myObject = new INPCObject()
let someClassWithStoredEventObject = new SomeClassWithStoredEventObject(myObject)
myObject.Age <- 12.0
myObject.Age <- 24.0
let myObject = Unchecked.defaultof<INPCObject>
GC.Collect();
GC.WaitForPendingFinalizers();

let testItsNull x =
    if myObject = Unchecked.defaultof<INPCObject> then
        printfn "Yes it null now, so setting value should be an issue"
    try
        myObject.Age <- 35.0
    with
    |:? System.NullReferenceException as ex -> printfn "NullReferenceException! %s " (ex.Message); 

testItsNull myObject

let myObject2 = new INPCObject()
printfn "Assigning new Event Source object"
someClassWithStoredEventObject.EventSourceObject <- myObject2
myObject2.Age <- 35.0
myObject2.Age <- 89.0

Which when run gives the following output, which as you can see allows the original event source to be garbage collected:

image

Further Reading III

http://weblogs.asp.net/podwysocki/archive/2009/08/21/f-first-class-events-creating-and-disposing-handlers.aspx

F# blog posts which borrows ideas from Rx, to allow event subscriptions to return an IDisposable, such that they can be disposed using the standard .Dispose() method

Further Reading IV

Observable module in F#,

Some of Rx in F#, we will be covering this is a later post