I want to find, if there is a same divisor between y,x and z,y following:
myFunc [x,y,z] = if y `div` x == z `div` y then True else False
But here I get True even if the divisor is not the same, let´s assume we have
x = 32
y = 64
z = 129
I suppose the problem is with div, which only makes int division. Is there any int to float divison in haskell that I could use to solve it?
div is floor division. It returns floor of a/b. Change your function to:
myFunc [x,y,z] = (y `foo` x) == (z `foo` y) where foo a b = (fromIntegral a) / (fromIntegral b)
Related
I'm new to Haskell and want to faktor an integer by trial division up to its square root.
Trying this snippet on replit.com:
firstfaktor n = head [x | x <- [2.. floor (sqrt n)], n `mod` x == 0]
main = do
print $ head [x | x <- [2.. floor (sqrt 91)], 91 `mod` x == 0]
print $ firstfaktor 91
I'd expect the second print to have the same output as the first namely 7, but it doesn't work and I don't understand the long error message.
Your firstfaktor uses n twice: once in sqrt n, where it requires the type of n to be a type of the RealFrac typeclass, and once for n `mod` x where it requires the type of n to be an instance of the Integral typeclass.
While technically possible to make a number type that is an instance of both, it does not make much sense to do that. You can make use of fromIntegral :: (Integral a, Num b) => a -> b to convert an item of a type that is a member of the Integral typeclass to any Num type, so we can use this with:
firstfaktor :: Integral a => a -> a
firstfaktor n = head [x | x <- [2.. floor (sqrt (fromIntegral n))], n `mod` x == 0]
The function will however still raise an error if it can not find any faktor for the given number.
A simpler option might however be to take items as long as the square of these items is less than or equal to n, so:
firstfaktor :: Integral a => a -> a
firstfaktor n = head [x | x <- takeWhile (\y -> y*y <= n) [2 ..], n `mod` x == 0]
I am currently trying to implement the Sieve of Atkin in Haskell
In step 3 on the Wikipedia article on the Sieve of Atkin I need to find the number of Integer solutions to multiple equations.
However my solution to the first of these equations (4x² + y² = n, x > 0, y > 0
with n being a entry in a list of positive Integers) produces an infinite loop upon a query with any n.
This is my code for this part of the problem so far:
eq1 :: Integer -> Integer
eq1 n = eq1_ n []
eq1_ :: Integer -> [(Integer, Integer)] -> Integer
eq1_ n list | (x > 0) && (y > 0) && (n == 4*(x^2) + (y^2)) && (notElem ((x,y)) list) = eq1_ n ([(x, y)] ++ list)
| otherwise = toInteger (length list)
where
x = floor (sqrt (fromIntegral ((n - y^2) `div` 4)))
y = floor (sqrt (fromIntegral (n - 4*(x^2))))
It is loaded just fine by WinGHCi, but when I query e.g. eq1 0 it just stays in an infinite loop and has to be interrupted before producing an answer. I suspect it goes in a loop between the two assignments of x and y.
How can I prevent this? Is this even possible?
Edit: Realised where the infinite loop must be.
I'm going to start by reformatting your code a tad to make it more readable. Line breaks are helpful! Also, the order of operations can reduce the weight of parentheses. Side note:
f x | e1 && e2 && e3 = e4
can also be written
f x | e1
, e2
, e3
= e4
which may be easier on the eyes.
eq1 :: Integer -> Integer
eq1 n = eq1_ n []
eq1_ :: Integer -> [(Integer, Integer)] -> Integer
eq1_ n list
| x > 0 &&
y > 0 &&
n == 4*x^2 + y^2 &&
notElem (x,y) list
= eq1_ n ([(x, y)] ++ list)
| otherwise
= toInteger (length list)
where
isqrt = floor . sqrt . fromIntegral
x = isqrt $ (n - y^2) `div` 4
y = isqrt $ n - 4*(x^2)
Now I can immediately see that the logic is wonky. Given n, you calculate x and y. Then you either stop or call the function recursively. On the recursive call, however, you're guaranteed to stop! So even if you were otherwise right, you'd definitely have a semantic problem, always returning 0 or 1.
But as you've seen, that's not the only problem. You're also defining x in terms of y and y in terms of x. Now there are important situations where such mutual recursion is useful. But when the mutually recursive values are "atomic" things like integers, you're sure to get an infinite loop. Haskell won't solve the equations for you; that's your job!
Here's my suggestion:
Start with a brute force list comprehension solution:
sols n
= [(x,y)
|x <- takeWhile (\p -> 4 * p^2 < n) [1..]
,y <- takeWhile (\q -> f x y <= n) [1..]
,f x y = n]
where
f x y = 4*x^2+y^2
Next, you can use an approximate integer square root to narrow the search space for y:
sols n
= [(x,y)
|x <- takeWhile (\p -> 4 * p^2 < n) [1..]
,y <- takeWhile
(\q -> f x y <= n)
[floor(sqrt(fromIntegral(n-4*x^2)))..]
,f x y = n]
where
f x y = 4*x^2+y^2
modPow :: Int -> Int -> Int -> Int
-- Pre: 1 <= m <= sqrt(maxint)
modPow x y n
|even y = (((x^halfy) `mod` n)^2) `mod` n
|otherwise = (x `mod` n)*(x ^ (y-1) `mod` n) `mod` n
where halfy = round (y/2)
REPORT ON TERMINAL:
Recursion.hs:39:19:
No instance for (RealFrac Int) arising from a use of ‘round’
In the expression: round (y / 2)
In an equation for ‘halfy’: halfy = round (y / 2)
In an equation for ‘modPow’:
modPow x y n
| even y = (((x ^ halfy) `mod` n) ^ 2) `mod` n
| otherwise = (x `mod` n) * (x ^ (y - 1) `mod` n) `mod` n
where
halfy = round (y / 2)
Recursion.hs:39:27:
No instance for (Fractional Int) arising from a use of ‘/’
In the first argument of ‘round’, namely ‘(y / 2)’
In the expression: round (y / 2)
In an equation for ‘halfy’: halfy = round (y / 2)
In halfy = round (y/2), you have y :: Int. However, the (/) operator is defined in the Fractional typeclass (which Int is not an instance of; think about which Int could represent e.g. 3/2).
However, there are also the integer division operators div and quot which will give you rounded, Int results. So just replace that definition of halfy with
halfy = y `quot` 2
This will recover your inteded behaviour of halfy since, forgetting about the typing issues for a moment, the fractional part of y/2 is always going to be either 0 or 0.5, and round rounds both towards 0:
Prelude> round (1/2) :: Int
0
Prelude> round (-1/2) :: Int
0
Prelude> 1 `quot` 2 :: Int
0
Prelude> (-1) `quot` 2 :: Int
0
Prelude> (-1) `div` 2 :: Int -- This doesn't recover the same behaviour for negative y!
-1
A really simple question: I want to implement the multiplication of 2 integers in Haskell.
What I wrote doesn't compile:
mult :: Int -> Int -> Int
mult x 1 = x
mult 1 y = y
mult x y = x + (mult x-1 y)
The problem is the last statement. I've tried writing it as:
mult x y = x + (mult x-1 y)
and also
mult x y = x + (mult(x-1,y))
The error I get is:
Couldn't match expected type `Int' with actual type `Int -> Int'
In the return type of a call of `mult'
I don't know why the compiler would say that mult returns an Int -> Int when it clearly returns an Int.
You have to put x-1 into brackets! Like so
mult x y = x + (mult (x-1) y)
By the way, this does not compute the multiplication of x and y :-)
Try some examples... it's a little mistake only.
In
mult x y = x + (mult x-1 y)
the expression within the parentheses parses as:
(mult x) - (1 y)
And so the compiler thinks the first argument to (-) is mult x, which is an Int -> Int function because just one argument (rather than two) is being passed. Instead, you want:
mult x y = x + mult (x-1) y
It's a simple parser issue. The compiler is reading mult x-1 y as ((-) (mult x) y) when what you mean is mult (x-1) y. Function application binds very tightly in Haskell, so it's sometimes better to use too many parentheses rather too few, especially while you're still learning the basics of the language.
The error occurs because the type of (mult x) is Int -> Int but the type of y is Int, and you can't subtract those two things.
Background
For fun, I'm trying to write a property for quick-check that can test the basic idea behind cryptography with RSA.
Choose two distinct primes, p and q.
Let N = p*q
e is some number relatively prime to (p-1)(q-1) (in practice, e is usually 3 for fast encoding)
d is the modular inverse of e modulo (p-1)(q-1)
For all x such that 1 < x < N, it is always true that (x^e)^d = x modulo N
In other words, x is the "message", raising it to the eth power mod N is the act of "encoding" the message, and raising the encoded message to the dth power mod N is the act of "decoding" it.
(The property is also trivially true for x = 1, a case which is its own encryption)
Code
Here are the methods I have coded up so far:
import Test.QuickCheck
-- modular exponentiation
modExp :: Integral a => a -> a -> a -> a
modExp y z n = modExp' (y `mod` n) z `mod` n
where modExp' y z | z == 0 = 1
| even z = modExp (y*y) (z `div` 2) n
| odd z = (modExp (y*y) (z `div` 2) n) * y
-- relatively prime
rPrime :: Integral a => a -> a -> Bool
rPrime a b = gcd a b == 1
-- multiplicative inverse (modular)
mInverse :: Integral a => a -> a -> a
mInverse 1 _ = 1
mInverse x y = (n * y + 1) `div` x
where n = x - mInverse (y `mod` x) x
-- just a quick way to test for primality
n `divides` x = x `mod` n == 0
primes = 2:filter isPrime [3..]
isPrime x = null . filter (`divides` x) $ takeWhile (\y -> y*y <= x) primes
-- the property
prop_rsa (p,q,x) = isPrime p &&
isPrime q &&
p /= q &&
x > 1 &&
x < n &&
rPrime e t ==>
x == (x `powModN` e) `powModN` d
where e = 3
n = p*q
t = (p-1)*(q-1)
d = mInverse e t
a `powModN` b = modExp a b n
(Thanks, google and random blog, for the implementation of modular multiplicative inverse)
Question
The problem should be obvious: there are way too many conditions on the property to make it at all usable. Trying to invoke quickCheck prop_rsa in ghci made my terminal hang.
So I've poked around the QuickCheck manual a bit, and it says:
Properties may take the form
forAll <generator> $ \<pattern> -> <property>
How do I make a <generator> for prime numbers? Or with the other constraints, so that quickCheck doesn't have to sift through a bunch of failed conditions?
Any other general advice (especially regarding QuickCheck) is welcome.
Here's one way to make a QuickCheck-compatible prime-number generator (stealing a Sieve of Eratosthenes implementation from http://en.literateprograms.org/Sieve_of_Eratosthenes_(Haskell)):
import Test.QuickCheck
newtype Prime = Prime Int deriving Show
primes = sieve [2..]
where
sieve (p:xs) = Prime p : sieve [x | x <- xs, x `mod` p > 0]
instance Arbitrary Prime where
arbitrary = do i <- arbitrary
return $ primes!!(abs i)
It can be used in QuickCheck like so:
prop_primes_dont_divide (Prime x) (Prime y) = x == y || x `mod` y > 0
For your use, you'd replace p and q with (Prime p) and (Prime q) in your property.
OK so here's what I did.
Top of file
{-# LANGUAGE NoMonomorphismRestriction #-}
import Test.QuickCheck
import Control.Applicative
All code as given in the question, except for prop_rsa. That was (obviously) heavily modified:
prop_rsa = forAll primePair $ \(p,q) ->
let n = p*q
in forAll (genUnder n) $ \x ->
let e = 3
t = (p-1)*(q-1)
d = mInverse e t
a `powModN` b = modExp a b n
in p /= q &&
rPrime e t ==>
x == (x `powModN` e) `powModN` d
The type for primePair is Gen (Int, Int), and the type for genUnder is Int -> Gen Int. I'm not exactly sure what the magic is behind forAll but I'm pretty sure this is correct. I've done some ad-hoc adjustments to 1) make sure it fails if I mess up the conditions and 2) make sure the nested forAll is varying the value of x across test cases.
So here's how to write those generators. Once I realized that <generator> in the documentation just meant something of type Gen a, it was cake.
genNonzero = (\x -> if x == 0 then 1 else x) `fmap` arbitrary
genUnder :: Int -> Gen Int
genUnder n = ((`mod` n) . abs) `fmap` genNonzero
genSmallPrime = ((\x -> (primes !! (x `mod` 2500))) . abs) `fmap` arbitrary
primePair :: Gen (Int, Int)
primePair = (,) <$> genSmallPrime <*> genSmallPrime
primePair took some trial and error for me to get right; I knew that some combinators like that should work, but I'm still not as familiar with fmap, <$> and <*> as I'd like to be. I restricted the computation to only select from among the first 2500 primes; otherwise it apparently wanted to pick some really big ones that took forever to generate.
Random thing to note
Thanks to laziness, d = mInverse e t isn't computed unless the conditions are met. Which is good, because it's undefined when the condition rPrime e t is false. In English, an integer a only has a multiplicative inverse (mod b) when a and b are relatively prime.