I have a tuple study that I want to write out in Haskell. It's given that S = {〈x, y〉| 2x y = 7, x ∈B, y ∈B }, where B = {1, 2.. 20}. I figured out that the answer is S = {〈1, 5〉,〈2, 3〉,〈3, 1〉}. However, when I type it out in a online Haskell compiler https://app.codingrooms.com/w/Yr2VJHj0yb9S, I either get way too many tuples, or I get an error message Snapshot, Haskell compiler . I've tried changing up the code by separating x and y, or by alterating between parenthesis and square brackets, but I haven't had any success. Does anyone have any advice for me? Thanks in advance!
Code in Haskell compiler:
b = [1, 2.. 20]
s = [(x,y)|x <- b, y <- b, let 2*x y = 7]
main = do
print s
CodePudding user response:
Your let 2*x y = 7
is actually short for let ( ) (2*x) y = 7
, so you are redefining the ( )
function. But one of the parameters has as pattern (2*x)
, which is not a valid pattern. But even if that would work, it will produce tuples for the entire B×B space, so not the correct answer.
You can let x
and y
enumerate over the list B
and filter with 2*x y == 7
:
f b = [ (x, y) | x <- b, y <- b, 2*x y == 7 ]
but probably it is slightly more efficient to perform a membership check:
f b = [ (x, y) | x <- b, let y = 7 - 2*x, y `elem` b ]
both yield:
ghci> f [1 .. 20]
[(1,5),(2,3),(3,1)]
CodePudding user response:
To apply filtering in the list comprehension you need to provide predicate - 2*x y == 7
:
s = [(x,y)|x <- b, y <- b, 2*x y == 7]
not the let
declaration you have tried to use.