Reputation: 3406
Haskell "No instance for" error
Haskell Error: "No instance for (Enum [Int])
Function definition problems (No instance for … arising from)
No instance for Num String arising from the literal `1'
I am very new to Haskell, and functional programming in general. In addition, I am aware that the questions above are very similar, but I have not been able to find a solution for my problem anywhere. The following code is meant to find the factors of a number input:
fc4 :: Double -> IO ()
check :: Double -> Double -> IO ()
fc4 a = check a (sqrt a)
check a b = if rem a b == 0 then print (b, div a b) else print () >> if b > 1 then check a (b-1) else putStrLn ("Done.")
I have attempted switching from Double
to Integer
and back with every possible combination, but every one fails with the same error:
No instance for (Integral Double) arising from a use of 'rem'
I have also tried explicitly using fromIntegral
and toInteger
on the arguments of rem
, but no combination I have attempted has avoided this problem. I also see by the documentation that the type for rem
is Integral a => a -> a -> a
, and so it seems that using the same type for a
and b
would always work, whether it be Double
or Integer
.
Am I on to something? Have I made some terrible rookie mistakes? For reference, here is a C++ version of what I hope to achieve. Thanks in advance!
Upvotes: 1
Views: 9212
Reputation: 531868
You could simply replace Double
with Integer
in the type signatures, since you need to use a value whose type is an instance of the Integral
type class, which defines div
and rem
. However, sqrt
only returns values that are instances of the Floating
type class, and there aren't any types that are instances of both.
The simple solution is to use ceiling
to get an integral value that is just slightly larger than sqrt n
, which will not affect the correctness of your algorithm.
check :: Integer -> Integer -> IO ()
check a b = ... -- same as before
fc4 :: Integer -> IO ()
--fc4 a = check a (ceiling (sqrt a)) -- because I didn't bother testing
fc4 a = check a (floor (sqrt (fromIntegral a)))
Upvotes: 7