1+ using System . Runtime . CompilerServices ;
2+ using System . Runtime . InteropServices ;
3+ using System . Runtime . Intrinsics . X86 ;
4+ using Genbox . FastData . Generators . Helpers ;
5+
6+ namespace Genbox . FastData . Benchmarks . Benchmarks ;
7+
8+ /// <summary>Benchmarks the difference between normal modulus and FastMod</summary>
9+ public class FastModBenchmarks
10+ {
11+ private readonly uint _value = 3_000_000_000 ; //Note: Do not make this const!
12+ private readonly ushort _mod = 1024 ; //Note: Do not make this const!
13+ private const ushort _modConst = 1024 ;
14+
15+ private readonly ulong _mult = MathHelper . GetFastModMultiplier ( int . MaxValue ) ;
16+ private readonly uint _mult2 = GetFastModMultiplierSmall ( 3000 ) ;
17+
18+ [ Benchmark ]
19+ public uint Const ( ) => _value % 1024 ;
20+
21+ [ Benchmark ]
22+ public uint ConstAdd ( ) => _value & 1023 ;
23+
24+ [ Benchmark ]
25+ public long Var ( ) => _value % _mod ;
26+
27+ [ Benchmark ]
28+ public long VarConst ( ) => _value % _modConst ;
29+
30+ [ Benchmark ]
31+ public long VarAdd ( ) => _value & 1023 ;
32+
33+ [ Benchmark ]
34+ public ulong FastMod ( ) => MathHelper . FastMod ( _value , 1024 , _mult ) ;
35+
36+ [ Benchmark ]
37+ public ulong FastModSmall ( ) => FastModSmall ( 3000 , 1024 , _mult2 ) ;
38+
39+ [ MethodImpl ( MethodImplOptions . AggressiveInlining ) ]
40+ private static uint GetFastModMultiplierSmall ( uint divisor ) => unchecked ( ( uint . MaxValue / divisor ) + 1 ) ;
41+
42+ [ MethodImpl ( MethodImplOptions . AggressiveInlining ) ]
43+ private static ulong FastModSmall ( ushort value , ushort divisor , uint multiplier ) => ( ( ulong ) ( multiplier * value ) * divisor ) >> 32 ;
44+ }
0 commit comments