Why does this list comprehension return an empty list?

Hi Folks, I have a list of singletons: xs = [("a")] f is a function that, given an argument x, it returns the argument: f x = x g is a function that, given an argument x, it returns the empty list: g x = [] I have a list comprehension that extracts the singletons from xs using f and g, and creates a pair from their output: [(a,b) | a <- f xs, b <- g xs] I executed this and the result is the empty list: [] That is odd. Why is the empty list the result? Consider this list comprehension that extracts the singletons from xs using f only, and creates a pair by matching up the singleton from xs with the empty list: [(a,[]) | a <- f xs] The result is this: [("a",[])] That is the result that I expected to get with the first list comprehension. Would you explain why this: [(a,b) | a <- f xs, b <- g xs] yields [], whereas this: [(a,[]) | a <- f xs] yields [("a",[])]? Also, how would I modify this: [(a,b) | a <- f xs, b <- g xs] so that it produces this: [("a",[])] /Roger

On 2013-07-23 10:53, Costello, Roger L. wrote:
I have a list of singletons:
xs = [("a")]
f is a function that, given an argument x, it returns the argument:
f x = x
g is a function that, given an argument x, it returns the empty list:
g x = []
I have a list comprehension that extracts the singletons from xs using f and g, and creates a pair from their output:
[(a,b) | a <- f xs, b <- g xs]
I executed this and the result is the empty list:
[]
That is odd. Why is the empty list the result?
Consider how the list comprehension looks like when written as monadic code: f xs >>= \a -> g xs >>= \b -> return (a,b) I.e. "for each element 'a' drawn from the result of "f sx", draw an element 'b' from the result of "g xs" and yield a new element "(a,b)". So the resulting list will always be 'length (f xs) * length (g xs)' items in length. Consequently, if either of the two lists is empty, the result will be empty. -- Frerich Raabe - raabe@froglogic.com www.froglogic.com - Multi-Platform GUI Testing

Hi, Dnia 2013-07-23, wto o godzinie 08:53 +0000, Costello, Roger L. pisze:
Hi Folks,
I have a list of singletons:
xs = [("a")]
f is a function that, given an argument x, it returns the argument:
f x = x
g is a function that, given an argument x, it returns the empty list:
g x = []
I have a list comprehension that extracts the singletons from xs using f and g, and creates a pair from their output:
[(a,b) | a <- f xs, b <- g xs]
I executed this and the result is the empty list:
[]
That is odd. Why is the empty list the result?
Becouse g xs has zero elements. Look at this example: [(x,x) | x <- []] => [] Empty list has zero elements.
Consider this list comprehension that extracts the singletons from xs using f only, and creates a pair by matching up the singleton from xs with the empty list:
[(a,[]) | a <- f xs]
The result is this:
[("a",[])]
That is the result that I expected to get with the first list comprehension.
Would you explain why this:
[(a,b) | a <- f xs, b <- g xs]
yields [], whereas this:
[(a,[]) | a <- f xs]
yields [("a",[])]?
Also, how would I modify this:
[(a,b) | a <- f xs, b <- g xs]
so that it produces this:
[("a",[])]
Define g as: g xs = [[]] or maybe better: g _ = [[]] Now it has 1 element - empty list. Best regards, Emanuel

On Tue, Jul 23, 2013 at 10:53 AM, Costello, Roger L.
Hi Folks,
I have a list of singletons:
xs = [("a")]
The type of that, as written, is [String].
f is a function that, given an argument x, it returns the argument:
f x = x
g is a function that, given an argument x, it returns the empty list:
g x = []
I have a list comprehension that extracts the singletons from xs using f and g, and creates a pair from their output:
[(a,b) | a <- f xs, b <- g xs]
I executed this and the result is the empty list:
[]
That is odd. Why is the empty list the result?
If you say it out loud what you are looking for it makes sense: construct a list tuples containing all combinations of 'a' and 'b' where 'a' is taken from the list 'f xs' and 'b' from the list 'g xs'. Now 'g xs' is empty, which means there is no possible value for 'b' to take, hence there is no way to create even a single such tuple. /M -- Magnus Therning OpenPGP: 0xAB4DFBA4 email: magnus@therning.org jabber: magnus@therning.org twitter: magthe http://therning.org/magnus

Le 23 juil. 2013 10:54, "Costello, Roger L."
Hi Folks,
I have a list of singletons:
xs = [("a")]
f is a function that, given an argument x, it returns the argument:
f x = x
g is a function that, given an argument x, it returns the empty list:
g x = []
I have a list comprehension that extracts the singletons from xs using f
and g, and creates a pair from their output:
[(a,b) | a <- f xs, b <- g xs]
I executed this and the result is the empty list:
[]
That is odd. Why is the empty list the result?
This is pretty normal since there are no elements in "g xs" so b can takes no values. You have got some excellent answers on that but I think your problem is more fundamental :
f x = x
This function does nothing or more precisely it is the identity, you can replace "f anything" by "anything" and have exactly the same result.
g x = []
This function just takes anything and returns an empty list. So
[(a,b) | a <- f xs, b <- g xs]
Is exactly the same as :
[(a,b) | a <- xs, b <- [] ]
If xs is ["a"] that becomes
[(a,b) | a <- ["a"], b <- [] ]
I think those f and g didn't work like that in your mind so could you explain what you thought they should do (with some examples maybe). -- Jedaï

On Tue, Jul 23, 2013 at 3:53 PM, Costello, Roger L.
Also, how would I modify this:
[(a,b) | a <- f xs, b <- g xs]
so that it produces this:
[("a",[])]
Try: [(a,b) | a <- f xs | b <- g xs] Note the 2nd parallel bar. You may have to enable a Parallel List Comprehension pragma or somesuch. Everyone else has given great explanations about your curious definitions of f and g and why the original does what it does. Well worth looking into. -- Kim-Ee

On Tue, Jul 23, 2013 at 3:53 PM, Costello, Roger L.
I have a list comprehension that extracts the singletons from xs using f and g, and creates a pair from their output:
[(a,b) | a <- f xs, b <- g xs]
I executed this and the result is the empty list:
[]
That is odd. Why is the empty list the result?
For the same reason that the cartesian product of any set with the empty set is the empty set. Also,
I have a list of singletons: xs = [("a")]
is immediately suspect, since you have xs:: [String], whereas "a list of singletons" appears to lean quite a lot more toward [Char], which is just String. -- Kim-Ee
participants (6)
-
Chaddaï Fouché
-
Costello, Roger L.
-
Emanuel Koczwara
-
Frerich Raabe
-
Kim-Ee Yeoh
-
Magnus Therning