Checking divisibility for Bool always results in false - haskell

I'm trying to check for leap years, which are "years either divisible by 400 or divisible by 4 but not divisible by 100." Removing one of the conditions still doesn't return a true on actual leap years. Only the z value in the tuple counts toward the divisibility but these conditions never return a True value for an actual leap year.
checkLeap :: (Int, Int, Int) -> Bool
checkLeap (x,y,z)
| z == 400 `mod` 1 = True
| z == 4 `mod` 1 && z /= 100 `mod` 1 = True
| otherwise = False

mod is 0 when it's divisible, and it also doesn't go all the way on the end in Haskell. Try this instead:
checkLeap :: (Int, Int, Int) -> Bool
checkLeap (x,y,z)
| z `mod` 400 == 0 = True
| z `mod` 4 == 0 && z `mod` 100 /= 0 = True
| otherwise = False

Related

Write a function that lists numbers from n to m by k number of steps. If the step size is negative list them in descending order

Implement the interval2 :: Int -> Int -> Int -> [Int] function,that lists numbers from the first parameter to the third parameter, the stepping's size is the second parameter. Using [n..m], [n,k..m] or [n..] is prohibited.
For example:
interval2 1 1 10 == [1,2..10]
interval2 10 1 0 == [10,11..0]
interval2 10 (-1) 0 == [10,9..0]
interval2 1 2 10 == [1,3..10]
interval2 10 2 0 == [10,12..0]
interval2 0 (-2) (-10) == [0,(-2)..(-10)]
interval2 1 (-1) 10 == [1,0..10]
interval2 0 (-10) (-1000) == [0,(-10)..(-1000)]
So far, I've managed to write some cases, but they didn't do the job very well.
interval2 x y z | x < z && y > 0 = [x] ++ interval2 (x+y) y z
| x < z && y < 0 = [x] ++ interval2 (x-y) y z
| x > z && y > 0 = [x] ++ interval2 (x-y) y z
| x > z && y < 0 = [x] ++ interval2 (x+y) y z
| x == z || x > z = [z]
There are basically two cases when you should emit a new value:
if x <= z and y > 0; and
if x >= z and y < 0.
In both cases that means the list contains x as first element and should recurse on the interval with x+y. In case none of these conditions are not met, then we have reached the end of the list.
This thus means that the function looks like:
interval2 x y z
| (x <= z && y > 0) || (x >= z && y < 0) = …
| otherwise = …
where I leave implementing … as an exercise.
Naming is important. When learning, naming is very important.
What is x? What is y? What is z? Are all of them the same, conceptually?
No, as the exercise describes it, it is
interval2 :: Int -> Int -> Int -> [Int]
interval2 from stepSize to =
this already gets you half way there towards the solution. Yes it does.
Or actually, you have a contradiction. According to the title of your post, it is
interval2b :: Int -> Int -> Int -> [Int]
interval2b from numSteps to =
But in any case, solving the first one first, you seem to get lost in the multitude of tests. Instead of doing all of them in one function, why not do a test to decide which of several functions to use to do the job; then write each of those functions being already able to assume certain things, namely those which we've tested for:
interval2 from stepSize to
| stepSize > 0 = increasing from
| stepSize < 0 = decreasing from
| otherwise = []
where
increasing from
| from
and now it is easy to see which test to perform here, isn't it?
> to = []
| otherwise = from : increasing ....
decreasing from
| from
and similarly here.
.........
..................
I hope this helps you manage this complexity so you'll be able to complete this code yourself.

SumFromTo , A Recursive Function

I am trying to do a recursive function that should give the sum of all integers between and including its two arguments. For example,
sumFromTo 5 8 is 5 + 6 + 7 + 8 = 26. If the first argument is greater than the
second, the function should return 0.
This is what I got currently but I am a beginner and I don't think I did it right
sumFromTo :: Int -> Int -> Int
sumFromTo x y
| x == 1 = 1
| y == 1 = 1
| x > 1 && y > 1 = x + y sumFromTo (x - 1)
| otherwise = 0
Any help please?
You can use a list comprehension to do this very simply:
sumFromTo :: Int -> Int -> Int
sumFromTo x y = sum [x..y]
However, I'm not sure what you'd want to do if x == y.
In the code you've given, your recursive definition isn't correct syntax. You've only given sumFromTo one argument, when it needs two, and you appear to have missed a + between the y and the function.
λ> sumFromTo 8 5
0
λ> sumFromTo 5 8
26
λ> sumFromTo 8 8
8
λ>
[a..b] means a list with a step of 1 between a and b, so [1..4] is [1,2,3,4]
Thanks to Phylogenesis, here is a recursive definition:
sumFromTo :: Int -> Int -> Int
sumFromTo x y
| x > y = 0
| x == y = x
| otherwise = x + sumFromTo (x + 1) y
I think you make the problem too complex if you want to implement this with recursion. Basically there are two cases:
one where the lower bound is greater than the upper bound, in which case the sum is zero; and
one where the lower bound is less than or equal to the upper bound.
The first case (1) can be expressed by writing:
sumFromTo x y | x > y = 0
In the second case, the result is the lower bound plus the sum of the lowerbound plus one to the upper bound, so:
| otherwise = x + sumFromTo (x+1) y
and putting these together:
sumFromTo :: (Num a, Ord a) => a -> a -> a
sumFromTo x y | x > y = 0
| otherwise = x + sumFromTo (x+1) y

If n is divisible by 2 return true - haskell

im trying to do a question in Haskell. I've just begun learning the language and can't get my head around this question.
I need to return a boolean if n is divisible by 2, it will be true, otherwise false. Heres what i've gotten so far and it doesnt work...
is_even :: Int -> Bool
is_even n
| n `mod` 2 == 0 return True
| otherwise return False
Fixed it myself...
is_even :: Int -> Bool
is_even n
| n `mod` 2 == 0 = True
|otherwise = False

Checking if the return is an int - Haskell

So what I would like to do is find out if the answer is an integer and return that answer. Here is an example. If I input 5, it would return 1.
The example checks if the integer is divisible by 5 or 6 and then returns it if it is.
division :: Int -> Int
division 5
| 5 / 5 == Int || 5 / 6 == Int = Int
| otherwise = 2
Use mod
f x | x `mod` 5 == 0 = x `div` 5
f x | x `mod` 6 == 0 = x `div` 6
f _ = 2
This will return x/5 if it is an int, if not, it will return x/6 if it is an int, else it will just return 2.

Problems with types in Haskell

I have some problems with the different types in Haskell, how can I solve this?
Couldn't match expected type Integer with actual type Int -> t0 -> t0
Thanks
isPrime :: Int -> Bool
isPrime number
| (number == 1) || (number == 2) = True
| even number = False
| otherwise = checkDiv number (fromInteger (`sqrt` number))
checkDiv :: Int -> Int -> Bool
checkDiv number divisor
| number == 2 = True
| (floor number `mod` divisor) == 0 = False
| otherwise = checkDiv number $ divisor - 1
I've figured out the modifications to get the code to compile, but it does not actually find primes. I had to change
fromInteger (`sqrt` number)
to
floor $ sqrt $ fromIntegral number
The backtick notation around a function name is to turn it in to an infix "operator" of sorts, so you could do
mod x y
or
x `mod` y
but not
`mod` x y
Next, you were using fromInteger instead of fromIntegral, which is the one that works on Ints (Int and Integer are different types). Finally, I removed the floor from number in the second guard of checkDiv, since number is already an Int.
isPrime :: Int -> Bool
isPrime number
| (number == 1) || (number == 2) = True
| even number = False
| otherwise = checkDiv number (floor $ sqrt $ fromIntegral number)
checkDiv :: Int -> Int -> Bool
checkDiv number divisor
| number == 2 = True
| (number `mod` divisor) == 0 = False
| otherwise = checkDiv number $ divisor - 1
So let's work through your code so that you can see what's going on. If I were to compute checkDiv 17 4 (4 is floor $ sqrt $ fromIntegral 17), it would perform
checkDiv 17 4
| 17 == 2 No
| 17 `mod` 4 == 0 No
| otherwise = checkDiv 17 (4 - 1) = checkDiv 17 3
checkDiv 17 3
| 17 == 2 No
| 17 `mod` 3 == 0 No
| otherwise = checkDiv 17 (3 - 1) = checkDiv 17 2
checkDiv 17 2
| 17 == 2 No
| 17 `mod` 2 == 0 No
| otherwise = checkDiv 17 (2 - 1) = checkDiv 17 1
checkDiv 17 1
| 17 == 2 No
| 17 `mod` 1 == 0 Yes = False
But 17 is prime! Do you see where your algorithm is doing something wrong?

Resources