On Tuesday, 27 December 2016 05:37:43 UTC+7, Robin Heggelund Hansen wrote: > > Part I: Evan is already aware of this issue, you can see the full > discussion in this github issue: > https://github.com/elm-lang/elm-compiler/issues/1528 > The short of it is that the code generator part of the compiler is not > aware of type information, and adding this would be a serious undertaking. > It will probably come at some point, as there are interesting optimizations > that can be made, like the one mentioned >
Although it is good to see that Even is aware of the issue, it is discouraging to learn that the type information is not retained by the code generator and therefore this improvement is part of a "huge project"; thus the linked issue has been closed. The person who raised the original issue developed some timing results that showed only about a 20% speed improvement for the particular code use. However, when I compare the above tight loop written directly in JavaScript, the difference here is about 700%! Of course, real use cases won't be quite this large, but I could see a fairly tight loop being 300% (+/- 100%) faster. > > Part II: Bitwise operators are inlined in 0.18, which gave a noticable > performance boost in libraries like Skinney/elm-array-exploration and > mgold/random-pcg. Having it available as a function (just like +, -, * > etc.) allows more flexibility like currying. > I checked and you are right that these functions are now inlined. The only other thing they should also have is infix for those with two operands for better (conventional) clarity of code, but this is no biggy. It turns out that the huge slowdown as compared to equivalent JavaScript code is another instance of the Part I problem as it is caused by a *call to `Native_Utils.eq` which is even less efficient than `Native_Utils.**cmp`* resulting in about a 1500% slowdown compared to JavaScript for the following code: import Bitwise as Bw testProg : Int -> Int testProg n = -- do some work let loop i = if Bw.and i 0x3FFFFFFF == 0x3FFFFFFF then i else loop (i + 1) in loop n which compiles to: var _user$project$Temp1482804013226255$testProg = function (n) { var loop = function (i) { loop: while (true) { if (_elm_lang$core$Native_Utils.eq(i & 1073741823, 1073741823)) { return i; } else { var _v0 = i + 1; i = _v0; continue loop; } } }; return loop(n); }; with `Native_Utils.eq` defined as: function eq(x, y) { var stack = []; var isEqual = eqHelp(x, y, 0, stack); var pair; while (isEqual && (pair = stack.pop())) { isEqual = eqHelp(pair.x, pair.y, 0, stack); } return isEqual; } function eqHelp(x, y, depth, stack) { if (depth > 100) { stack.push({ x: x, y: y }); return true; } if (x === y) { return true; } ... For this use case, there are a succession of conditions which won't cost that much as explained in the opening post, but it is twice as slow as the example in Part I because *there are typically two nested calls of the functions `Native_Utils.eq` with `Native_Utils.eqHelp` called from within it!* This is the reason it is twice as slow as the example in Part I. If and when the issue as of Part I is fixed, then bitwise operations will be fixed too. Meanwhile, for real work programs with intensive bitwise tight loop computations, Elm is likely up to about 10 times slower than JavaScript and for general numeric tight loop calculations about 5 times slower, which I find unacceptable. -- You received this message because you are subscribed to the Google Groups "Elm Discuss" group. To unsubscribe from this group and stop receiving emails from it, send an email to elm-discuss+unsubscr...@googlegroups.com. For more options, visit https://groups.google.com/d/optout.