I'm creating a Matrix module in Haskell and I want to use QuickCheck to test some properties of my code. Specifically I want to generate random matrices that have an associated inverse. The following is my attempt at creating a QuickCheck generator that generates such matrices.
invertibleMatrix :: (Num a, Arbitrary a) => Gen (Matrix a)
invertibleMatrix = do s <- choose (2,10)
a <- vectorOf s (vector s)
if (det (Matrix a) == 0) then
invertibleMatrix
else
return (Matrix a)
The code first creates a size between 2 and 10 and then a vector of vectors of this size. If the determinant is zero then the matrix is not invertible and so I call invertibleMatrix recursively. Otherwise I return the new matrix.
The trouble is, this code does not terminate when I put it in a property to test. (I think that it's constantly creating the same s x s matrix of zero elements which obviously doesn't have an inverse and so it goes into an infinite loop). What am I doing wrong? How do I fix this? Thanks.
Mark
squareMatrix :: (Num a, Arbitrary a) => Gen (Matrix a)
squareMatrix = do s <- choose (2,6)
a <- vectorOf s (vector s)
return (Matrix a)
invertibleMatrix :: (Num a, Arbitrary a) => Gen (Matrix a)
invertibleMatrix = suchThat squareMatrix ((/=0) . det)
In case anyone wants to know, this is the solution.
Mark