5. F# FOR PROFIT
Time to Market
Efficiency
Correctness
Complexity
* applied to Analytic components
6. TIME TO MARKET
speed development by 50 percent or more,
European IB
order of magnitude increase in productivity,
GameSys
7. EFFICIENCY
processes that used to require hours now take just minutes, Grange
Insurance
performance is 10× better than the C++ that it replaces, Aviva
10. C# & F# BEST FRIENDS
FOREVER
Kaggle Testimonial
The fact that F# targets the CLR
was also critical - even though we
have a large existing code base in
C#, getting started with F# was an
easy decision because we knew we
could use new modules right away.
12. DEFECT RATE
I am both a C# dev and an F# dev. I can
only offer subjective anecdotal evidence
based on my experience of delivering
projects in both languages (I am too
busy delivering software to do anything
else).
That said, the one stat in the summary
that I find most compelling is the defect
rate. I have now delivered three
business critical projects written in F#. I
am still waiting for the first bug to
come in.
Simon Cousins, Power Company
13. DEPENDENCY INJECTION
F#
type VerySimpleStockTraderImpl
(analysisService:IStockAnalysisService,
brokerageService:IOnlineBrokerageService) =
interface IAutomatedStockTrader with
member this.ExecuteTrades() =
() // ...
C#
public class VerySimpleStockTraderImpl
: IAutomatedStockTrader
{
private readonly
IStockAnalysisService analysisService;
private readonly
IOnlineBrokerageService brokerageService;
public VerySimpleStockTraderImpl(
IStockAnalysisService analysisService,
IOnlineBrokerageService brokerageService)
{
this.analysisService = analysisService;
this.brokerageService = brokerageService;
}
public void ExecuteTrades()
{
// ...
}
}
14. NUNIT
F# NUnit
module MathTest
open NUnit.Framework
let [<Test>] ``2 + 2 should equal 4``() =
Assert.AreEqual(2 + 2, 4)
C# NUnit
using NUnit.Framework;
[TestFixture]
public class MathTest
{
[Test]
public void
TwoPlusTwoShouldEqualFour()
{
Assert.AreEqual(2 + 2, 4);
}
}
18. .NET MOCKING LIBRARY
type ITime =
abstract GetHour : unit -> int
type ImageCalculator (time:ITime) =
member this.GetImageForTimeOfDay() =
let hour = time.GetHour()
if hour > 6 && hour < 21
then "sun.jpg"
else "moon.jpg"
let [<Test>] `` at 01:00 the moon image should show `` () =
let time = Mock().Setup(fun (x:ITime) -> x.GetHour()).Returns(1)
let calculator = ImageCalculator(time.Create())
let image = calculator.GetImageForTimeOfDay()
Assert.AreEqual("moon.jpg", image)
19. F# OBJECT EXPRESSION
type ITime =
abstract GetHour : unit -> int
type ImageCalculator (time:ITime) =
member this.GetImageForTimeOfDay() =
let hour = time.GetHour()
if hour > 6 && hour < 21
then "sun.jpg"
else "moon.jpg“
let [<Test>] ``at 01:00 the moon image should show`` () =
let time = { new ITime with member mock.GetHour() = 01 }
let calculator = ImageCalculator(time)
let image = calculator.GetImageForTimeOfDay()
Assert.AreEqual("moon.jpg", image)
20. HIGHER-ORDER FUNCTION
let imageCalculator getHour =
fun () ->
let hour = getHour()
if hour > 6 && hour < 21
then "sun.jpg"
else "moon.jpg"
let [<Test>] ``at 01:00 the moon image should show`` () =
let getHour () = 01
let getImageForHourOfDay = imageCalculator getHour
let image = getImageForHourOfDay ()
Assert.AreEqual("moon.jpg", image)
21. MOCKING
F# Foq
let ``order sends mail if unfilled``() =
// setup data
let order = Order("TALISKER", 51)
let mailer = mock()
order.SetMailer(mailer)
// exercise
order.Fill(mock())
// verify
verify <@ mailer.Send(any()) @> once
C# Moq
public void OrderSendsMailIfUnfilled()
{
// setup data
var order = new Order("TALISKER", 51);
var mailer = new Mock<MailService>();
order.SetMailer(mailer.Object);
// exercise
order.Fill(Mock.Of<Warehouse>());
// verify
mailer.Verify(mock =>
mock.Send(It.IsAny<string>()),
Times.Once());
}
26. CELLZ
type formula =
| Neg of formula
| Exp of formula * formula
| ArithmeticOp of
formula * arithmetic * formula
| LogicalOp of
formula * logical * formula
| Num of UnitValue
| Ref of int * int
| Range of int * int * int * int
| Fun of string * formula list
29. MUTUAL RECURSION
type Folder(path:string) =
let files = Directory.GetFiles(path)
member folder.Files =
[|for file in files -> File(file,folder)|]
and File(filename: string, folder: Folder) =
member file.Name = filename
member file.Folder = folder
32. C#/F# INTEROP
Mostly it just works
Minor friction points
Equality
Explicit interfaces
Tuples & Union Types
Nulls
Tip: Read the F# Component Design Guidelines
33. EQUALITY: POP QUIZ
C# F#
var a =
new Order(Side.Bid, 99.9M, 5);
var b =
new Order(Side.Bid, 99.9M, 5);
return a == b;
let a = Order(Bid, 99.9M, 5)
let b = Order(Bid, 99.9M, 5)
a = b
35. C# ==
public static bool operator == (Order a, Order b)
{
return a.Equals(b);
}
public static bool operator != (Person a, Person b)
{
return !a.Equals(b);
}
36. F# -> C# ==
static member op_Equality (a:Order,b:Order) =
a = b
static member op_Inequality (a:Order,b:Order) =
a <> b