I am new to haskell and trying out some exercise.While trying to load the below code i am getting a binding error howmanytwoequal function.Can anyone please tell me as to what mistake i had done.
howmayoftwoequal :: Int->Int->Int
howmanyoftwoequal m n
|m==n =1
|otherwise =0
howmanyequal::Int->Int->Int->Int
howmanyequal m n o
| howmanyoftwoequal m n && howmanyoftwoequal n o =3
| howmanyoftwoequal m n || howmanyoftwoequal n o =2
|otherwise =1
You have several issues in your code:
Typo in howmanyoftwoequal type definition: you have 'howmayoftwoequal' instead of 'howmanyoftwoequal'
To use howmanyoftwoequal in boolean operations && and || its type should be Bool:
howmanyoftwoequal :: Int->Int->Bool
howmanyoftwoequal m n = m==n
Your definition of howManyEqual misses the case where m == o but m == n || n == o does not hold, which it seems should also be a valid case for it returning 2.
If you are trying to return the size of the largest equivalence class between m, n, and o, this can be achieved as follows:
largestEquivSize :: [Int] -> Int
largestEquivSize = maximum . map length . group . sort
howManyEqual :: Int -> Int -> Int -> Int
howManyEqual m n o = largestEquivSize [m, n, o]
With the added bonus that largestEquivSize is a lot more general (in fact its type is unnecessarily constrained here, and could be Ord a => [a] -> Int).
Related
I have to write function for calculating x^16 and x^20 that uses the least amount
of multiplication steps with Haskell. It is not allowed to use the built-in exponentiation operator ^. I`ve tried so many things,but nothing works... I already wrote it till x^8, i guess. What should i do as next?
square :: Integer -> Integer
square x = x * x
pow :: Integer -> Integer
pow x = square (square x)
pow1 :: Integer -> Integer
pow1 x = pow (pow x)
Let's formulate this the general way. (As dfeuer comments, this is actually not quite the general way, because sub-products could also be shared in other ways, not just in squaring; but for the given examples it's good enough.)
data Exponentiation
= Variable
| Multiplication Exponentiation Exponentiation
| Squaring Exponentiation
deriving (Eq, Show)
exponPower :: Exponentiation -> Int
exponPower Variable = 1
exponPower (Multiplication l r) = exponPower l + exponPower r
exponPower (Squaring e) = 2 * exponPower e
nMultiplications :: Exponentiation -> Int
nMultiplications Variable = 0
nMultiplications (Multiplication l r) = 1 + nMultiplications l + nMultiplications r
nMultiplications (Squaring e) = 1 + nMultiplications e
Now we can write a brute-force generator for finding the best possible strategy of multiplying to get a given power:
import Data.List (minimumBy)
import Data.Ord (comparing)
bestMulStrategy :: Int -> Exponentiation
bestMulStrategy 1 = Variable
bestMulStrategy n = minimumBy (comparing nMultiplications)
$ sqStrats ++ mulStrats
where sqStrats
| even n = [Squaring . bestMulStrategy $ n`quot`2]
| otherwise = []
mulStrats
= [ Multiplication l r
| nl <- [1..n-1]
, let l = bestMulStrategy nl
r = bestMulStrategy $ n-nl ]
That works, but it's very inefficient because we keep re-calculating the optimal strategy for the smaller sub-powers over and over, so already for 16 it takes a long time. A simple fix is to memoise the function:
import Data.MemoTrie
bestMulStrategy :: Int -> Exponentiation
bestMulStrategy = memo best
where best 1 = Variable
best n = minimumBy (comparing nMultiplications)
$ sqStrats ++ mulStrats
where sqStrats
| even n = [Squaring . bestMulStrategy $ n`quot`2]
| otherwise = []
mulStrats
= [ Multiplication l r
| nl <- [1..n-1]
, let l = bestMulStrategy nl
r = bestMulStrategy $ n-nl ]
And then we learn, unsurprisingly,
> bestMulStrategy 16
Squaring (Squaring (Squaring (Squaring Variable)))
For 20, it's a bit more interesting:
> bestMulStrategy 20
Squaring (Squaring (Multiplication Variable (Squaring (Squaring Variable))))
I don't think this is the unique optimum, but it certainly is an optimum (5 multiplications).
What's left to be done is, implementing those strategies as Haskell functions. That could be done with Template Haskell, but I think it's more instructive for you to do it yourself.
I am writing some code to work with arbitrary radix numbers in haskell. They will be stored as lists of integers representing the digits.
I almost managed to get it working, but I have run into the problem of converting a list of tuples [(a_1,b_1),...,(a_n,b_n)] into a single list which is defined as follows:
for all i, L(a_i) = b_i.
if there is no i such that a_i = k, a(k)=0
In other words, this is a list of (position,value) pairs for values in an array. If a position does not have a corresponding value, it should be set to zero.
I have read this (https://wiki.haskell.org/How_to_work_on_lists) but I don't think any of these methods are suitable for this task.
baseN :: Integer -> Integer -> [Integer]
baseN n b = convert_digits (baseN_digits n b)
chunk :: (Integer, Integer) -> [Integer]
chunk (e,m) = m : (take (fromIntegral e) (repeat 0))
-- This is broken because the exponents don't count for each other's zeroes
convert_digits :: [(Integer,Integer)] -> [Integer]
convert_digits ((e,m):rest) = m : (take (fromIntegral (e)) (repeat 0))
convert_digits [] = []
-- Converts n to base b array form, where a tuple represents (exponent,digit).
-- This works, except it ignores digits which are zero. thus, I converted it to return (exponent, digit) pairs.
baseN_digits :: Integer -> Integer -> [(Integer,Integer)]
baseN_digits n b | n <= 0 = [] -- we're done.
| b <= 0 = [] -- garbage input.
| True = (e,m) : (baseN_digits (n-((b^e)*m)) b)
where e = (greedy n b 0) -- Exponent of highest digit
m = (get_coef n b e 1) -- the highest digit
-- Returns the exponent of the highest digit.
greedy :: Integer -> Integer -> Integer -> Integer
greedy n b e | n-(b^e) < 0 = (e-1) -- We have overshot so decrement.
| n-(b^e) == 0 = e -- We nailed it. No need to decrement.
| n-(b^e) > 0 = (greedy n b (e+1)) -- Not there yet.
-- Finds the multiplicity of the highest digit
get_coef :: Integer -> Integer -> Integer -> Integer -> Integer
get_coef n b e m | n - ((b^e)*m) < 0 = (m-1) -- We overshot so decrement.
| n - ((b^e)*m) == 0 = m -- Nailed it, no need to decrement.
| n - ((b^e)*m) > 0 = get_coef n b e (m+1) -- Not there yet.
You can call "baseN_digits n base" and it will give you the corresponding array of tuples which needs to be converted to the correct output
Here's something I threw together.
f = snd . foldr (\(e,n) (i,l') -> ( e , (n : replicate (e-i-1) 0) ++ l')) (-1,[])
f . map (fromIntegral *** fromIntegral) $ baseN_digits 50301020 10 = [5,0,3,0,1,0,2,0]
I think I understood your requirements (?)
EDIT:
Perhaps more naturally,
f xs = foldr (\(e,n) fl' i -> (replicate (i-e) 0) ++ (n : fl' (e-1))) (\i -> replicate (i+1) 0) xs 0
I have the following Haskell functions:
expM :: Integer -> Integer -> Integer -> Integer
expM x y = rem (x^y)
And
exMME :: Integer -> Integer -> Integer -> Integer
exMME b 0 m = 1
exMME b e m = exMME' b e m 1 0 where
exMME' b e m c e'
| e' < e = exMME' b e m ((b * c) `mod` m) (e'+1)
| otherwise = c
What I want to do is use quickCheck to compare these two functions so i can see that they produce the same answer and which one is the fastest.
To test if they have the same answers I want to let QuickCheck create random positive integers with the exception of 0. So I created a Gen:
positives :: Gen Integer
positives =
do -- Pick an arbitrary integer:
x <- arbitrary
if (x == 0)
then return 1
else if (x < 0)
then return (-x)
else
return x
This works from the command line (ghci) but I have a prop:
prop_CompareAnswerExMFM :: Integer -> Integer -> Integer -> Bool
prop_CompareAnswerExMFM b e m =exMFM b e m == exM b e m
And each time i call this with QuickCheck prop_CompareAnswerExMFM it doesn't us my gen. After reading some stuff i toughed that i needed to define a instance:
instance Arbitrary Integer where
arbitrary = positives
This doesn't work because a arbitrary instance of Integer already exist. Again after some googling I say that the standard way to solve this is to use a wrapper:
newtype Positives = Positives Integer
deriving (Eq, Ord, Show)
instance Arbitrary Positives where
arbitrary = positives
positives :: Gen Positives
positives =
do -- Pick an arbitrary integer:
x <- arbitrary
if (x == 0)
then return 1
else if (x < 0)
then return (-x)
else
return x
But after playing around i keep getting errors like can't resolve this, No instance for (Num Positives) arising from the literal '0' or Can't make a derived instance of 'Num Positives'.
I think i'm making it way to complex for what i want but I just can't figure it out. I hope someone can help me or send me in the right direction.
Thanks
The problem with your code is that in positives the variable x has type Integer, so your return statements need to include the Positives constructor:
positives :: Gen Positives
positives =
do -- Pick an arbitrary integer:
x <- arbitrary
if (x == 0)
then return $ Positives 1
else if (x < 0)
then return $ Positives (-x)
else
return $ Positives x
If it helps, here is another way to write (a similarly working) positives function:
positives' :: Gen Positives
positives' = fmap (\x -> Positives (1 + abs x)) arbitrary
Here the arbitrary call is a Gen Integer, so the function argument to fmap has type Integer -> Positives.
To use your Positives newtype with QuickCheck you would use the Positives (de-)constructor to get at the Integer values:
prop_addition :: Positives -> Positives -> Bool
prop_addition (Positives a) (Positives b) = a + b >= 2
ghci> quickCheck prop_addtion
As #Carsten mentions in the comments, QuickCheck as a Positive a type which has an arbitrary instance for numeric and ordered types a.
Here's a quick way that doesn't require much understanding of QuickCheck but is a bit of a hack:
prop_CompareAnswerExMFM :: Integer -> Integer -> Integer -> Bool
prop_CompareAnswerExMFM b e m =
exMFM absB absE absM == exM absB absE absM
where -- following guarantees args are positive integers > 0
absB = 1 + abs b
absE = 1 + abs e
absM = 1 + abs m
and then you can just use
quickCheck prop_factored
I have this code to work out the sum of squares of integers in the range of m:n
sumsquares :: Integral a=> Int -> Int -> Int -> Int
sumsquares m n middle
| m > n = error "First number cannot be bigger than second number"
|m==n = m*m
|otherwise = m*m + sumsquares (m+1)n
How would i redefine the function sumsquares for this purpose?
If there is more than one number in the range m:n, compute the middle of the range and add the sum of the squares of (m:middle) to sum of the squares (middle+1:n),
otherwise there is only one number in the range m:n, so m = = n, and the solution is just the square of m. (Note that with this approach the recursion combines two half- solutions: each sub-problem is approximately half in size of the overall problem).
In your original function, the class constraint Integral a in the type signature is obsolete (a is not mentioned anywhere else in the signature, is it?). Furthermore, the third parameter of the function (middle) remains unused. Hence, you could have written it as
sumsquares :: Int -> Int -> Int
sumsquares m n
| m > n = error "First number cannot be bigger than second number"
| m == n = m * m
| otherwise = m * m + sumsquares (m + 1) n
Rewriting it to move from a decrease-and-conquer scheme to a strict divide-and-conquer scheme then just involves adapting the recursive case accordingly:
sumsquares :: Int -> Int -> Int
sumsquares m n
| m > n = error "First number cannot be bigger than second number"
| m == n = m * m
| otherwise = let middle = (m + n) `div` 2
in sumsquares m middle + sumsquares (middle + 1) n
The question remains, of course, why you would want to make this change. One reason could be that you are preparing your algorithm to be adapted for parallelisation: then, indeed, divide-and-conquer is often a better fit than decrease-and-conquer.
I am a beginner in Haskell and I am stuck in a simple recursion function.
I am trying to define a function rangeProduct which when given natural numbers m and n returns the product
m*(m+1)...(n-1)*n
The function should return 0 when n is smaller than m.
What I've tried:
rangeProduct :: Int -> Int -> Int
rangeProduct m n
| m > n = 0
| otherwise = m * n * rangeProduct (m+1)(n-1)
But this is wrong because in the otherwise guard, when m gets bigger and n smaller, at some point m will get bigger than n and it will get 0 causing all what it has done so far to get multiplied by zero, resulting in 0 everytime I run the function.
I know the answer is simple but I am stuck. Can anyone help? Thanks!
Why bother incrementing and decrementing at the same time? Just go in one direction:
rangeProduct m n
| m > n = 0
| m == n = n
| otherwise = m * rangeProduct (m + 1) n
Although you could easily define this without recursion as
rangeProduct :: Integer -> Integer -> Integer
rangeProduct m n
| m > n = 0
| otherwise = product [m..n]