Skip to content

Instantly share code, notes, and snippets.

@AndreyAkinshin
Created December 4, 2016 07:12
Show Gist options
  • Save AndreyAkinshin/bd7746cb6c1e991349a8bb06ab43610f to your computer and use it in GitHub Desktop.
Save AndreyAkinshin/bd7746cb6c1e991349a8bb06ab43610f to your computer and use it in GitHub Desktop.
DotNextMoscow2016
using System;
using System.Diagnostics;
using System.Linq;
using BenchmarkDotNet.Attributes;
using BenchmarkDotNet.Attributes.Jobs;
using BenchmarkDotNet.Jobs;
using BenchmarkDotNet.Running;
// BenchmarkDotNet v0.10.1
namespace DotNext
{
public class AllJitsJob : JobConfigBaseAttribute
{
public AllJitsJob() : base(Job.LegacyJitX86, Job.LegacyJitX64, Job.RyuJitX64, Job.Mono)
{
}
}
[AllJitsJob]
public class MinBench
{
const int N = 100001;
private int[] a, b, c;
public enum StrategyKind
{
Const,
Random
}
[Params(StrategyKind.Const, StrategyKind.Random)]
public StrategyKind Strategy;
[Setup]
public void Setup()
{
a = new int[N];
b = new int[N];
c = new int[N];
var rnd = new Random(42);
for (int i = 0; i < N; i++)
{
switch (Strategy)
{
case StrategyKind.Const:
{
a[i] = 42;
b[i] = 42;
}
break;
case StrategyKind.Random:
{
a[i] = rnd.Next();
b[i] = rnd.Next();
}
break;
}
}
}
[Benchmark]
public void MinA()
{
for (int i = 0; i < N; i++)
{
int x = a[i], y = b[i];
c[i] = Math.Min(x, y);
}
}
[Benchmark]
public void MinB()
{
for (int i = 0; i < N; i++)
{
int x = a[i], y = b[i];
c[i] = x < y ? x : y;
}
}
[Benchmark]
public void MinC()
{
for (int i = 0; i < N; i++)
{
int x = a[i], y = b[i];
c[i] = x & ((x - y) >> 31) | y & (~(x - y) >> 31);
}
}
}
[AllJitsJob]
public class DivBench
{
const int N = 100001;
private int[] a, b;
public DivBench()
{
a = new int[N];
b = new int[N];
var rnd = new Random(42);
for (int i = 0; i < N; i++)
a[i] = rnd.Next();
}
[Benchmark]
public void Div3A()
{
for (int i = 0; i < N; i++)
b[i] = a[i] / 3;
}
[Benchmark]
public void Div3B()
{
for (int i = 0; i < N; i++)
b[i] = (int) ((a[i] * 0xAAAAAAAB) >> 33);
}
}
[LegacyJitX86Job]
public class StackVsRegistersBench
{
private const int N = 100001;
[Params(false, true)] public bool InvokeCtor;
private long frequency;
[Setup]
public void Setup()
{
if (InvokeCtor)
frequency = Stopwatch.Frequency;
}
[Benchmark]
public double Sum()
{
double x = 1, y = 1;
for (int i = 0; i < N; i++)
x = x + y;
return x;
}
[Benchmark]
public double Sum2()
{
double x = 1, y = 1;
var sw = Stopwatch.StartNew();
for (int i = 0; i < N; i++)
x = x + y;
sw.Stop();
return x;
}
}
[LegacyJitX86Job, RyuJitX64Job]
public class DenormBench
{
[Params(100000, 1000000)] public int N;
[Benchmark]
public double PowerA()
{
double res = 1.0;
for (int i = 0; i < N; i++)
res = res * 0.96;
return res;
}
private double resB;
[Benchmark]
public double PowerB()
{
resB = 1.0;
for (int i = 0; i < N; i++)
resB = resB * 0.96;
return resB;
}
[Benchmark]
public double PowerC()
{
double res = 1;
for (int i = 0; i < N; i++)
res = res * 0.9 + 0.1 - 0.1;
return res;
}
}
[AllJitsJob]
public class SumBench
{
private double[] a;
[Params(4000)] public int N;
[Setup]
public void Setup()
{
var rnd = new Random(42);
a = new double[N];
for (int i = 0; i < N; i++)
a[i] = rnd.NextDouble();
}
[Benchmark]
public double Bcl() => a.Sum();
[Benchmark]
public double Loop()
{
double sum = 0;
for (int i = 0; i < a.Length; i++)
sum += a[i];
return sum;
}
[Benchmark]
public double Unroll()
{
double sum = 0;
for (int i = 0; i < a.Length; i += 4)
sum += a[i] + a[i + 1] + a[i + 2] + a[i + 3];
return sum;
}
}
internal class Program
{
public static void Main(string[] args)
{
new BenchmarkSwitcher(typeof(Program).Assembly).RunAll();
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment