sklose / NCalc2

expression evaluator for .NET with built-in compiler
MIT License
166 stars 58 forks source link

Implements a two-phase parse for expressions #82

Closed david-brink-talogy closed 7 months ago

david-brink-talogy commented 8 months ago

ANTLR4's default prediction mode is more powerful, but slower. This PR implements a two-phase parse, the first using the faster SLL mode, falling back to the slower, but more powerful LL mode on failure.

This may address #78

See https://medium.com/pragmatic-programmers/maximizing-parser-speed-9766aaaab0c0

david-brink-talogy commented 8 months ago

Results appear mixed.

Before change: https://ci.appveyor.com/project/sklose/ncalc2/builds/48865720

[00:01:04] ------------------------------------------------------------
[00:01:04] Formula: 5 * 2 = 2 * 5 && (1 / 3.0) * 3 = 1
[00:01:04] Expression: 158,863.48 evaluations / sec
[00:01:04] Lambda: 60,945,880.06 evaluations / sec
[00:01:04] Lambda Speedup: 38,263.68%%
[00:01:04] ------------------------------------------------------------
[00:01:05] ------------------------------------------------------------
[00:01:05] Formula: (4 * 12 / 7) + ((9 * 2) % 8)
[00:01:05] Expression: 234,288.83 evaluations / sec
[00:01:05] Lambda: 55,900,273.91 evaluations / sec
[00:01:05] Lambda Speedup: 23,759.56%%
[00:01:05] ------------------------------------------------------------
[00:01:05] ------------------------------------------------------------
[00:01:05] Formula: Foo([Param1] * 7, [Param2])
[00:01:05] Expression: 351,821.43 evaluations / sec
[00:01:05] Lambda: 99,088,386.84 evaluations / sec
[00:01:05] Lambda Speedup: 28,064.40%%
[00:01:05] ------------------------------------------------------------
[00:01:05] ------------------------------------------------------------
[00:01:05] Formula: [Param1] * 7 + [Param2]
[00:01:05] Expression: 407,567.39 evaluations / sec
[00:01:05] Lambda: 101,646,676.15 evaluations / sec
[00:01:05] Lambda Speedup: 24,839.85%%
[00:01:05] ------------------------------------------------------------
[00:01:05] ------------------------------------------------------------
[00:01:05] Formula: [Param1] * 7 + [Param2]
[00:01:05] Expression: 461,207.39 evaluations / sec
[00:01:05] Lambda: 93,449,210.35 evaluations / sec
[00:01:05] Lambda Speedup: 20,161.86%%
[00:01:05] ------------------------------------------------------------

After change: https://ci.appveyor.com/project/sklose/ncalc2/builds/48866282

[00:01:08] ------------------------------------------------------------
[00:01:08] Formula: 5 * 2 = 2 * 5 && (1 / 3.0) * 3 = 1
[00:01:08] Expression: 138,617.39 evaluations / sec
[00:01:08] Lambda: 66,229,551.63 evaluations / sec
[00:01:08] Lambda Speedup: 47,678.67%%
[00:01:08] ------------------------------------------------------------
[00:01:09] ------------------------------------------------------------
[00:01:09] Formula: (4 * 12 / 7) + ((9 * 2) % 8)
[00:01:09] Expression: 262,643.11 evaluations / sec
[00:01:09] Lambda: 74,161,969.74 evaluations / sec
[00:01:09] Lambda Speedup: 28,136.78%%
[00:01:09] ------------------------------------------------------------
[00:01:09] ------------------------------------------------------------
[00:01:09] Formula: Foo([Param1] * 7, [Param2])
[00:01:09] Expression: 491,892.14 evaluations / sec
[00:01:09] Lambda: 102,923,013.59 evaluations / sec
[00:01:09] Lambda Speedup: 20,823.90%%
[00:01:09] ------------------------------------------------------------
[00:01:09] ------------------------------------------------------------
[00:01:09] Formula: [Param1] * 7 + [Param2]
[00:01:09] Expression: 706,603.92 evaluations / sec
[00:01:09] Lambda: 117,980,179.33 evaluations / sec
[00:01:09] Lambda Speedup: 16,596.79%%
[00:01:09] ------------------------------------------------------------
[00:01:09] ------------------------------------------------------------
[00:01:09] Formula: [Param1] * 7 + [Param2]
[00:01:09] Expression: 819,865.00 evaluations / sec
[00:01:09] Lambda: 106,791,969.24 evaluations / sec
[00:01:09] Lambda Speedup: 12,925.56%%
[00:01:09] ------------------------------------------------------------