Last active
February 29, 2016 23:43
-
-
Save aholmes/cff5800d07b5aec573c7 to your computer and use it in GitHub Desktop.
Comparison of FP and OOP approaches to benchmark a simple operation. https://www.reddit.com/r/javascript/comments/48alyu/functional_programming_for_javascript_people/d0inhqq
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Diagnostics; | |
using System.Linq; | |
namespace ConsoleApplication3 | |
{ | |
class Program | |
{ | |
static int add(int x , int y) | |
{ | |
return x + y; | |
} | |
static void Main(string[] args) | |
{ | |
const int runs = 500; | |
const int executions = 100000000; | |
var sw = new Stopwatch(); | |
var rand = new Random(); | |
var runAvgs = new long[runs]; | |
var i = 0; | |
var run = 0; | |
while (run < runs) | |
{ | |
sw.Start(); | |
while (i < executions) | |
{ | |
add(rand.Next(), rand.Next()); | |
i++; | |
} | |
sw.Stop(); | |
runAvgs[run] = sw.ElapsedMilliseconds; | |
run++; | |
} | |
Console.WriteLine(string.Format("Avg time: {0}ms", runAvgs.Average())); | |
Console.Read(); | |
} | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
.namespace ConsoleApplication3 | |
{ | |
.class private auto ansi beforefieldinit ConsoleApplication3.Program | |
extends [mscorlib]System.Object | |
{ | |
// Methods | |
.method private hidebysig static | |
int32 'add' ( | |
int32 x, | |
int32 y | |
) cil managed | |
{ | |
// Method begins at RVA 0x2050 | |
// Code size 9 (0x9) | |
.maxstack 2 | |
.locals init ( | |
[0] int32 | |
) | |
IL_0000: nop | |
IL_0001: ldarg.0 | |
IL_0002: ldarg.1 | |
IL_0003: add | |
IL_0004: stloc.0 | |
IL_0005: br.s IL_0007 | |
IL_0007: ldloc.0 | |
IL_0008: ret | |
} // end of method Program::'add' | |
.method private hidebysig static | |
void Main ( | |
string[] args | |
) cil managed | |
{ | |
// Method begins at RVA 0x2068 | |
// Code size 152 (0x98) | |
.maxstack 3 | |
.entrypoint | |
.locals init ( | |
[0] class [System]System.Diagnostics.Stopwatch, | |
[1] class [mscorlib]System.Random, | |
[2] int64[], | |
[3] int32, | |
[4] int32, | |
[5] bool, | |
[6] bool | |
) | |
IL_0000: nop | |
IL_0001: newobj instance void [System]System.Diagnostics.Stopwatch::.ctor() | |
IL_0006: stloc.0 | |
IL_0007: newobj instance void [mscorlib]System.Random::.ctor() | |
IL_000c: stloc.1 | |
IL_000d: ldc.i4 500 | |
IL_0012: newarr [mscorlib]System.Int64 | |
IL_0017: stloc.2 | |
IL_0018: ldc.i4.0 | |
IL_0019: stloc.3 | |
IL_001a: ldc.i4.0 | |
IL_001b: stloc.s 4 | |
IL_001d: br.s IL_0067 | |
// loop start (head: IL_0067) | |
IL_001f: nop | |
IL_0020: ldloc.0 | |
IL_0021: callvirt instance void [System]System.Diagnostics.Stopwatch::Start() | |
IL_0026: nop | |
IL_0027: br.s IL_0041 | |
// loop start (head: IL_0041) | |
IL_0029: nop | |
IL_002a: ldloc.1 | |
IL_002b: callvirt instance int32 [mscorlib]System.Random::Next() | |
IL_0030: ldloc.1 | |
IL_0031: callvirt instance int32 [mscorlib]System.Random::Next() | |
IL_0036: call int32 ConsoleApplication3.Program::'add'(int32, int32) | |
IL_003b: pop | |
IL_003c: ldloc.3 | |
IL_003d: ldc.i4.1 | |
IL_003e: add | |
IL_003f: stloc.3 | |
IL_0040: nop | |
IL_0041: ldloc.3 | |
IL_0042: ldc.i4 100000000 | |
IL_0047: clt | |
IL_0049: stloc.s 5 | |
IL_004b: ldloc.s 5 | |
IL_004d: brtrue.s IL_0029 | |
// end loop | |
IL_004f: ldloc.0 | |
IL_0050: callvirt instance void [System]System.Diagnostics.Stopwatch::Stop() | |
IL_0055: nop | |
IL_0056: ldloc.2 | |
IL_0057: ldloc.s 4 | |
IL_0059: ldloc.0 | |
IL_005a: callvirt instance int64 [System]System.Diagnostics.Stopwatch::get_ElapsedMilliseconds() | |
IL_005f: stelem.i8 | |
IL_0060: ldloc.s 4 | |
IL_0062: ldc.i4.1 | |
IL_0063: add | |
IL_0064: stloc.s 4 | |
IL_0066: nop | |
IL_0067: ldloc.s 4 | |
IL_0069: ldc.i4 500 | |
IL_006e: clt | |
IL_0070: stloc.s 6 | |
IL_0072: ldloc.s 6 | |
IL_0074: brtrue.s IL_001f | |
// end loop | |
IL_0076: ldstr "Avg time: {0}ms" | |
IL_007b: ldloc.2 | |
IL_007c: call float64 [System.Core]System.Linq.Enumerable::Average(class [mscorlib]System.Collections.Generic.IEnumerable`1<int64>) | |
IL_0081: box [mscorlib]System.Double | |
IL_0086: call string [mscorlib]System.String::Format(string, object) | |
IL_008b: call void [mscorlib]System.Console::WriteLine(string) | |
IL_0090: nop | |
IL_0091: call int32 [mscorlib]System.Console::Read() | |
IL_0096: pop | |
IL_0097: ret | |
} // end of method Program::Main | |
.method public hidebysig specialname rtspecialname | |
instance void .ctor () cil managed | |
{ | |
// Method begins at RVA 0x210c | |
// Code size 8 (0x8) | |
.maxstack 8 | |
IL_0000: ldarg.0 | |
IL_0001: call instance void [mscorlib]System.Object::.ctor() | |
IL_0006: nop | |
IL_0007: ret | |
} // end of method Program::.ctor | |
} // end of class ConsoleApplication3.Program | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
open System | |
let add(x, y) = | |
x + y | |
[<EntryPoint>] | |
let main argv = | |
let runs = 500; | |
let executions = 100000000; | |
let sw = System.Diagnostics.Stopwatch(); | |
let rand = System.Random(); | |
let runAvgs = Array.create runs 0L; | |
let mutable i = 0; | |
let mutable run = 0; | |
while run < runs do | |
sw.Start(); | |
while i < executions do | |
add (rand.Next(), rand.Next()) |> ignore | |
i <- i + 1 | |
sw.Stop(); | |
runAvgs.[run] <- sw.ElapsedMilliseconds | |
run <- run + 1 | |
printf "Avg time: %dms\n\n" (runAvgs | |
|> Array.averageBy (fun e -> float e) | |
|> Convert.ToInt64) | |
Console.Read() |> ignore | |
0 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
.class private auto ansi '<Module>' | |
extends [mscorlib]System.Object | |
{ | |
} // end of class <Module> | |
.class public auto ansi abstract sealed Program | |
extends [mscorlib]System.Object | |
{ | |
.custom instance void [FSharp.Core]Microsoft.FSharp.Core.CompilationMappingAttribute::.ctor(valuetype [FSharp.Core]Microsoft.FSharp.Core.SourceConstructFlags) = ( | |
01 00 07 00 00 00 00 00 | |
) | |
// Nested Types | |
.class nested assembly auto ansi serializable beforefieldinit main@28 | |
extends class [FSharp.Core]Microsoft.FSharp.Core.FSharpFunc`2<int64, float64> | |
{ | |
// Methods | |
.method assembly specialname rtspecialname | |
instance void .ctor () cil managed | |
{ | |
// Method begins at RVA 0x2210 | |
// Code size 7 (0x7) | |
.maxstack 8 | |
IL_0000: ldarg.0 | |
IL_0001: call instance void class [FSharp.Core]Microsoft.FSharp.Core.FSharpFunc`2<int64, float64>::.ctor() | |
IL_0006: ret | |
} // end of method main@28::.ctor | |
.method public strict virtual | |
instance float64 Invoke ( | |
int64 e | |
) cil managed | |
{ | |
// Method begins at RVA 0x2218 | |
// Code size 4 (0x4) | |
.maxstack 8 | |
IL_0000: nop | |
IL_0001: ldarg.1 | |
IL_0002: conv.r8 | |
IL_0003: ret | |
} // end of method main@28::Invoke | |
} // end of class main@28 | |
// Methods | |
.method public static | |
int32 'add' ( | |
int32 x, | |
int32 y | |
) cil managed | |
{ | |
// Method begins at RVA 0x2050 | |
// Code size 5 (0x5) | |
.maxstack 8 | |
IL_0000: nop | |
IL_0001: ldarg.0 | |
IL_0002: ldarg.1 | |
IL_0003: add | |
IL_0004: ret | |
} // end of method Program::'add' | |
.method public static | |
int32 main ( | |
string[] argv | |
) cil managed | |
{ | |
.custom instance void [FSharp.Core]Microsoft.FSharp.Core.EntryPointAttribute::.ctor() = ( | |
01 00 00 00 | |
) | |
// Method begins at RVA 0x2058 | |
// Code size 410 (0x19a) | |
.maxstack 5 | |
.entrypoint | |
.locals init ( | |
[0] int32 runs, | |
[1] int32 executions, | |
[2] class [System]System.Diagnostics.Stopwatch sw, | |
[3] class [mscorlib]System.Random rand, | |
[4] int64[] runAvgs, | |
[5] int32 i, | |
[6] int32 run, | |
[7] int32, | |
[8] int32, | |
[9] class [FSharp.Core]Microsoft.FSharp.Core.FSharpFunc`2<int64, class [FSharp.Core]Microsoft.FSharp.Core.Unit>, | |
[10] int64, | |
[11] float64, | |
[12] int64[], | |
[13] class [FSharp.Core]Microsoft.FSharp.Core.FSharpFunc`2<int64, float64>, | |
[14] int64[], | |
[15] class [mscorlib]System.Collections.Generic.IEnumerable`1<int64>, | |
[16] class [mscorlib]System.Collections.Generic.IEnumerator`1<int64>, | |
[17] float64, | |
[18] float64, | |
[19] int32, | |
[20] float64, | |
[21] int32, | |
[22] class [mscorlib]System.IDisposable, | |
[23] float64, | |
[24] int32, | |
[25] int32 | |
) | |
IL_0000: nop | |
IL_0001: ldc.i4 500 | |
IL_0006: stloc.0 | |
IL_0007: ldc.i4 100000000 | |
IL_000c: stloc.1 | |
IL_000d: newobj instance void [System]System.Diagnostics.Stopwatch::.ctor() | |
IL_0012: stloc.2 | |
IL_0013: newobj instance void [mscorlib]System.Random::.ctor() | |
IL_0018: stloc.3 | |
IL_0019: ldloc.0 | |
IL_001a: ldc.i8 0 | |
IL_0023: call !!0[] [FSharp.Core]Microsoft.FSharp.Collections.ArrayModule::Create<int64>(int32, !!0) | |
IL_0028: stloc.s runAvgs | |
IL_002a: ldc.i4.0 | |
IL_002b: stloc.s i | |
IL_002d: ldc.i4.0 | |
IL_002e: stloc.s run | |
// loop start (head: IL_0030) | |
IL_0030: ldloc.s run | |
IL_0032: ldloc.0 | |
IL_0033: bge.s IL_007e | |
IL_0035: ldloc.2 | |
IL_0036: callvirt instance void [System]System.Diagnostics.Stopwatch::Start() | |
// loop start (head: IL_003b) | |
IL_003b: ldloc.s i | |
IL_003d: ldloc.1 | |
IL_003e: bge.s IL_0060 | |
IL_0040: ldloc.3 | |
IL_0041: callvirt instance int32 [mscorlib]System.Random::Next() | |
IL_0046: ldloc.3 | |
IL_0047: callvirt instance int32 [mscorlib]System.Random::Next() | |
IL_004c: call int32 Program::'add'(int32, int32) | |
IL_0051: stloc.s 7 | |
IL_0053: ldloc.s 7 | |
IL_0055: stloc.s 8 | |
IL_0057: ldloc.s i | |
IL_0059: ldc.i4.1 | |
IL_005a: add | |
IL_005b: stloc.s i | |
IL_005d: nop | |
IL_005e: br.s IL_003b | |
// end loop | |
IL_0060: ldloc.2 | |
IL_0061: callvirt instance void [System]System.Diagnostics.Stopwatch::Stop() | |
IL_0066: ldloc.s runAvgs | |
IL_0068: ldloc.s run | |
IL_006a: ldloc.2 | |
IL_006b: callvirt instance int64 [System]System.Diagnostics.Stopwatch::get_ElapsedMilliseconds() | |
IL_0070: stelem.any [mscorlib]System.Int64 | |
IL_0075: ldloc.s run | |
IL_0077: ldc.i4.1 | |
IL_0078: add | |
IL_0079: stloc.s run | |
IL_007b: nop | |
IL_007c: br.s IL_0030 | |
// end loop | |
IL_007e: ldstr "Avg time: %dms\n\n" | |
IL_0083: newobj instance void class [FSharp.Core]Microsoft.FSharp.Core.PrintfFormat`5<class [FSharp.Core]Microsoft.FSharp.Core.FSharpFunc`2<int64, class [FSharp.Core]Microsoft.FSharp.Core.Unit>, class [mscorlib]System.IO.TextWriter, class [FSharp.Core]Microsoft.FSharp.Core.Unit, class [FSharp.Core]Microsoft.FSharp.Core.Unit, int64>::.ctor(string) | |
IL_0088: call !!0 [FSharp.Core]Microsoft.FSharp.Core.ExtraTopLevelOperators::PrintFormat<class [FSharp.Core]Microsoft.FSharp.Core.FSharpFunc`2<int64, class [FSharp.Core]Microsoft.FSharp.Core.Unit>>(class [FSharp.Core]Microsoft.FSharp.Core.PrintfFormat`4<!!0, class [mscorlib]System.IO.TextWriter, class [FSharp.Core]Microsoft.FSharp.Core.Unit, class [FSharp.Core]Microsoft.FSharp.Core.Unit>) | |
IL_008d: stloc.s 9 | |
IL_008f: ldloc.s runAvgs | |
IL_0091: stloc.s 12 | |
IL_0093: newobj instance void Program/main@28::.ctor() | |
IL_0098: stloc.s 13 | |
IL_009a: ldloc.s 12 | |
IL_009c: stloc.s 14 | |
IL_009e: ldloc.s 14 | |
IL_00a0: box int64[] | |
IL_00a5: brfalse.s IL_00a9 | |
IL_00a7: br.s IL_00bc | |
IL_00a9: ldstr "array" | |
IL_00ae: newobj instance void [mscorlib]System.ArgumentNullException::.ctor(string) | |
IL_00b3: call !!0 [FSharp.Core]Microsoft.FSharp.Core.Operators::Raise<class [FSharp.Core]Microsoft.FSharp.Core.Unit>(class [mscorlib]System.Exception) | |
IL_00b8: pop | |
IL_00b9: nop | |
IL_00ba: br.s IL_00bd | |
IL_00bc: nop | |
IL_00bd: ldloc.s 14 | |
IL_00bf: unbox.any class [mscorlib]System.Collections.Generic.IEnumerable`1<int64> | |
IL_00c4: stloc.s 15 | |
IL_00c6: ldloc.s 15 | |
IL_00c8: box class [mscorlib]System.Collections.Generic.IEnumerable`1<int64> | |
IL_00cd: brfalse.s IL_00d1 | |
IL_00cf: br.s IL_00e4 | |
IL_00d1: ldstr "source" | |
IL_00d6: newobj instance void [mscorlib]System.ArgumentNullException::.ctor(string) | |
IL_00db: call !!0 [FSharp.Core]Microsoft.FSharp.Core.Operators::Raise<class [FSharp.Core]Microsoft.FSharp.Core.Unit>(class [mscorlib]System.Exception) | |
IL_00e0: pop | |
IL_00e1: nop | |
IL_00e2: br.s IL_00e5 | |
IL_00e4: nop | |
IL_00e5: ldloc.s 15 | |
IL_00e7: callvirt instance class [mscorlib]System.Collections.Generic.IEnumerator`1<!0> class [mscorlib]System.Collections.Generic.IEnumerable`1<int64>::GetEnumerator() | |
IL_00ec: stloc.s 16 | |
.try | |
{ | |
IL_00ee: ldc.r8 0.0 | |
IL_00f7: stloc.s 18 | |
IL_00f9: ldc.i4.0 | |
IL_00fa: stloc.s 19 | |
// loop start (head: IL_00fc) | |
IL_00fc: ldloc.s 16 | |
IL_00fe: callvirt instance bool [mscorlib]System.Collections.IEnumerator::MoveNext() | |
IL_0103: brfalse.s IL_0121 | |
IL_0105: ldloc.s 18 | |
IL_0107: ldloc.s 13 | |
IL_0109: ldloc.s 16 | |
IL_010b: callvirt instance !0 class [mscorlib]System.Collections.Generic.IEnumerator`1<int64>::get_Current() | |
IL_0110: callvirt instance !1 class [FSharp.Core]Microsoft.FSharp.Core.FSharpFunc`2<int64, float64>::Invoke(!0) | |
IL_0115: add | |
IL_0116: stloc.s 18 | |
IL_0118: ldloc.s 19 | |
IL_011a: ldc.i4.1 | |
IL_011b: add | |
IL_011c: stloc.s 19 | |
IL_011e: nop | |
IL_011f: br.s IL_00fc | |
// end loop | |
IL_0121: ldloc.s 19 | |
IL_0123: brtrue.s IL_0127 | |
IL_0125: br.s IL_0129 | |
IL_0127: br.s IL_0141 | |
IL_0129: call string [FSharp.Core]Microsoft.FSharp.Core.LanguagePrimitives/ErrorStrings::get_InputSequenceEmptyString() | |
IL_012e: ldstr "source" | |
IL_0133: newobj instance void [mscorlib]System.ArgumentException::.ctor(string, string) | |
IL_0138: call !!0 [FSharp.Core]Microsoft.FSharp.Core.Operators::Raise<class [FSharp.Core]Microsoft.FSharp.Core.Unit>(class [mscorlib]System.Exception) | |
IL_013d: pop | |
IL_013e: nop | |
IL_013f: br.s IL_0142 | |
IL_0141: nop | |
IL_0142: ldloc.s 18 | |
IL_0144: stloc.s 20 | |
IL_0146: ldloc.s 19 | |
IL_0148: stloc.s 21 | |
IL_014a: ldloc.s 20 | |
IL_014c: ldloc.s 21 | |
IL_014e: conv.r8 | |
IL_014f: div | |
IL_0150: stloc.s 17 | |
IL_0152: leave.s IL_0172 | |
} // end .try | |
finally | |
{ | |
IL_0154: ldloc.s 16 | |
IL_0156: isinst [mscorlib]System.IDisposable | |
IL_015b: stloc.s 22 | |
IL_015d: ldloc.s 22 | |
IL_015f: brfalse.s IL_0163 | |
IL_0161: br.s IL_0165 | |
IL_0163: br.s IL_016f | |
IL_0165: ldloc.s 22 | |
IL_0167: callvirt instance void [mscorlib]System.IDisposable::Dispose() | |
IL_016c: ldnull | |
IL_016d: pop | |
IL_016e: endfinally | |
IL_016f: ldnull | |
IL_0170: pop | |
IL_0171: endfinally | |
} // end handler | |
IL_0172: ldloc.s 17 | |
IL_0174: stloc.s 11 | |
IL_0176: ldloc.s 11 | |
IL_0178: stloc.s 23 | |
IL_017a: ldloc.s 23 | |
IL_017c: call int64 [mscorlib]System.Convert::ToInt64(float64) | |
IL_0181: stloc.s 10 | |
IL_0183: ldloc.s 9 | |
IL_0185: ldloc.s 10 | |
IL_0187: callvirt instance !1 class [FSharp.Core]Microsoft.FSharp.Core.FSharpFunc`2<int64, class [FSharp.Core]Microsoft.FSharp.Core.Unit>::Invoke(!0) | |
IL_018c: pop | |
IL_018d: call int32 [mscorlib]System.Console::Read() | |
IL_0192: stloc.s 24 | |
IL_0194: ldloc.s 24 | |
IL_0196: stloc.s 25 | |
IL_0198: ldc.i4.0 | |
IL_0199: ret | |
} // end of method Program::main | |
} // end of class Program |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment