Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to check fused vector function? #33

Open
Magalame opened this issue May 11, 2019 · 5 comments
Open

How to check fused vector function? #33

Magalame opened this issue May 11, 2019 · 5 comments

Comments

@Magalame
Copy link

Hi!

I'm having trouble with fused function, notably here:

mulSub :: Vector Double -> Vector Double -> Double
mulSub v1 v2 =  U.sum $ U.zipWith (*) v1 v2

v :: Vector Double
v = U.fromList [1,2,3]

mul :: Double 
mul = mulSub v v

inspect $ ('mul `hasNoType` ''Vector)

mul fails the test, although mulSub is fused. What would be a way around this issue?

@nomeata
Copy link
Owner

nomeata commented May 12, 2019

I would guess that because you use v twice, GHC doesn't inline it and fusion doesn't happen.

@Magalame
Copy link
Author

Magalame commented May 12, 2019

It seems like this:

v :: Vector Double
v = U.fromList [1,2,3]

u :: Vector Double
u = U.fromList [1,2,3]

mulSub :: Vector Double -> Vector Double -> Double
mulSub v1 v2 =  U.sum $ U.zipWith (*) v1 v2

mul :: Double 
mul = mulSub v u

inspect $ ('mul `hasNoType` ''Vector) 

still fails. Am I missing something?

@nomeata
Copy link
Owner

nomeata commented May 13, 2019

Use the Core :-) It should show you what’s happening. Likely GHC has combined v and u because they are the same. Or it is reluctant to inline to-level things.

Have you tried the following?

mulUpTo :: Double -> Double -> Double
mulUpTo x1 x2 = U.sum (U.zipWith (*) (U.fromList [0 .. x1]) (U.fromList [0 .. x2])
inspect $ ('mulUpto `hasNoType` ''Vector) 

These tests work better (and are more realistic!) if you don't use constant top-level values, but rather write functions. But in the end it depends on what you actually want to test for.

Also see haskell/vector#229

@Magalame
Copy link
Author

Unfortunately Core is a bit hard on the eye :/

A more practical example of what I'm actually trying to test is: I have a Matrix which contains the row data as a U.Vector, the number of row, and the number of column. And for example I want to write matrix multiplication such that multiply a (multiply a b) actually allocates only one matrix, the one containing the end result

@Magalame
Copy link
Author

So far I've been using weigh to measure allocation, and it turned out to be successful in most cases, but there seem to be some cases where it's not : fpco/weigh#37

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants