[Haskell-cafe] Floyd Warshall performance (again)
Roman Leshchinskiy
rl at cse.unsw.edu.au
Fri Apr 16 05:16:36 EDT 2010
On 16/04/2010, at 18:06, Mathieu Boespflug wrote:
> shortestPath :: [(Int, Int, Int)] -> UArray Int Int
> shortestPath g = runSTUArray $ do
> let mnew = newArray (0, SIZE * SIZE) 1
> mread arr i j = unsafeRead arr (i * SIZE + j)
> mwrite arr i j x = unsafeWrite arr (i * SIZE + j) x
> unsafeIOToST $ hSetBuffering stdout LineBuffering
> unsafeIOToST $ putStrLn "Allocating ..."
> pm <- mnew
> unsafeIOToST $ putStrLn "Allocating ... done"
> let loop1 SIZE = return ()
> loop1 k = let loop2 SIZE = return ()
> loop2 i = let loop3 SIZE = return ()
> loop3 j = do
> xij <- mread pm i j
> xik <- mread pm i k
> xkj <- mread pm k j
> mwrite pm i j (min xij (xik + xkj))
> loop3 (j + 1)
> in loop3 0 >> loop2 (i + 1)
> in loop2 0 >> loop1 (k + 1)
> loop1 0
> return pm
In general, GHC doesn't like nested loops. You might want to try the following structure:
loop1 SIZE = return ()
loop1 k = loop2 k 0
loop2 k SIZE = loop1 (k+1)
loop2 k i = loop3 k i 0
loop3 k i SIZE = loop2 k (i+1)
loop3 k i j = do
...
loop3 k i (j+1)
And, as Max suggested, the llvm backend ought to improve things.
Roman
More information about the Haskell-Cafe
mailing list