<div dir="ltr"><br><div class="gmail_extra"><br><div class="gmail_quote">On Thu, Jan 26, 2017 at 3:15 PM, Michael Snoyman <span dir="ltr"><<a href="mailto:michael@snoyman.com" target="_blank">michael@snoyman.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex"><div dir="ltr"><br><div class="gmail_extra"><br><div class="gmail_quote"><span class="gmail-">On Thu, Jan 26, 2017 at 3:05 PM, Johannes Waldmann <span dir="ltr"><<a href="mailto:johannes.waldmann@htwk-leipzig.de" target="_blank">johannes.waldmann@htwk-<wbr>leipzig.de</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">What Michael did not mention in the mail, but it's in his code:<br>
numerals defaulted to Integer, and the story changes (somewhat)<br>
if we force Int.<br>
<br>
I updated my measurements:<br>
<a href="http://www.imn.htwk-leipzig.de/~waldmann/etc/mob/" rel="noreferrer" target="_blank">http://www.imn.htwk-leipzig.de<wbr>/~waldmann/etc/mob/</a><br>
and ghc-8 looks better now - but not quite wins.<br>
<span><br>
> there's still some more low hanging fruit here<br>
<br>
</span>... for whom? What could we reasonably expect of the compiler here?<br>
It could do the strictification? the unboxing?<br>
<br>
It certainly could not replace Integer by Int,<br>
since the range of numerical values has no obvious bound.<br>
<br>
But then, all these Integers are small, but we pay quite an overhead<br>
(for represeting Int as Integer) which has increased for current ghcs?<br>
<div class="gmail-m_76061271359420953HOEnZb"><div class="gmail-m_76061271359420953h5"><br></div></div></blockquote><div><br></div></span><div>I meant that, if someone wanted to bring down allocations significantly, I would think there's still room for optimization. I was not commenting on what GHC should or shouldn't be capable of doing here. It would certainly be nice, for example, if it was capable of noticing the strictness involved and automatically unbox the STRefs, but that would be quite a feat.</div><div><br></div><div>I didn't investigate further myself, so I could be mistaken about the possibility to further reduce allocations. It was just a guess (thus the "I think").</div><span class="gmail-HOEnZb"><font color="#888888"><div><br></div><div>Michael</div></font></span></div></div></div>
</blockquote></div><br></div><div class="gmail_extra">As an example, upon reviewing the code I realized it was unnecessarily allocating a reference in the case of `k <= 0`. Fixing that reduces allocations to 800MB (from 1.9GB). This was a pretty easy change to make. A more involved change would be to share a mutable vector of larger size instead of allocating a new reference each time. I'm now intrigued enough by the problem that I'll probably do that next :)</div><div class="gmail_extra"><br></div><div class="gmail_extra"><div class="gmail_extra">#!/usr/bin/env stack</div><div class="gmail_extra">-- stack --resolver lts-7.14 --install-ghc exec --package mutable-containers -- ghc -O2 -with-rtsopts=-s</div><div class="gmail_extra">import <a href="http://Control.Monad.ST">Control.Monad.ST</a></div><div class="gmail_extra">import Data.Mutable</div><div class="gmail_extra"><br></div><div class="gmail_extra">a :: Int</div><div class="gmail_extra">  -> ST s Int</div><div class="gmail_extra">  -> ST s Int</div><div class="gmail_extra">  -> ST s Int</div><div class="gmail_extra">  -> ST s Int</div><div class="gmail_extra">  -> ST s Int</div><div class="gmail_extra">  -> ST s Int</div><div class="gmail_extra">a k x1 x2 x3 x4 x5</div><div class="gmail_extra">    | k <= 0 = do</div><div class="gmail_extra">        x3' <- x3</div><div class="gmail_extra">        x4' <- x4</div><div class="gmail_extra">        return $! x3' + x4'</div><div class="gmail_extra">    | otherwise = do</div><div class="gmail_extra">        kRef <- fmap asURef $ newRef k</div><div class="gmail_extra"><br></div><div class="gmail_extra">        let b = do</div><div class="gmail_extra">                k0 <- readRef kRef</div><div class="gmail_extra">                let k1 = k0 - 1</div><div class="gmail_extra">                writeRef kRef k1</div><div class="gmail_extra">                a k1 b x1 x2 x3 x4</div><div class="gmail_extra"><br></div><div class="gmail_extra">        x5' <- x5</div><div class="gmail_extra">        b' <- b</div><div class="gmail_extra">        return $! x5' + b'</div><div class="gmail_extra"><br></div><div class="gmail_extra"><br></div><div class="gmail_extra">main = print $ runST $ a</div><div class="gmail_extra">    22</div><div class="gmail_extra">    (return 1)</div><div class="gmail_extra">    (return (-1))</div><div class="gmail_extra">    (return (-1))</div><div class="gmail_extra">    (return 1)</div><div class="gmail_extra">    (return 0)</div></div></div>