如何在Haskell中使用理解力从嵌套列表中删除空列表

时间:2019-04-12 20:02:47

标签: haskell

我刚开始学习Haskell,并且开始研究理解理解,这使我可以通过为更大的集合提供条件来形成子集。

我试图做出一个理解,该理解采用一个嵌套列表(包含其他整数列表),并从中删除所有正奇数和空的内部列表。

testList= [-3]:[-5,8]:[[1,3,5,7,9],[],[4,6,8,10],[1,3,6,7,9],[],[1]]

removingOnlyPosOdds xxs = [ [x | x <-xs, not (odd x && x > 0 )] | xs <- xxs, [] /= xs ] 

testList应用于其上的理解功能之前,如下所示:

[[-3],[-5,8],[1,3,5,7,9],[],[4,6,8,10],[1,3,6,7,9],[],[1]]

应用removingOnlyPosOdds testList后

The outcome was 
[[-3],[-5,8],[],[4,6,8,10],[6],[]] 

所以我意识到函数描述中的"[] /= xs"正在删除已经存在的

仅在"[]"中的

testList内部列表;但不是由我从内部列表中删除正奇数引起的新的形成。

为了在代码方面也删除这些代码,下一步应该做什么?

我希望它看起来像

[[-3],[-5,8],[4,6,8,10],[6]]

是否有一种方法可以一概而论地概括理解能力?

或者还有另一种方法可以更好地处理事物的清除(例如,空的内部列表)并创建更指定的集合?

1 个答案:

答案 0 :(得分:3)

您可以添加一些额外的过滤器,并使用let子句防止两次进行相同的列表理解,例如:

removingOnlyPosOdds xxs = [ ys | xs <- xxs, let ys = [x | x <-xs, not (odd x && x > 0 )], not (null ys)  ]

或者我们可以添加一些额外的过滤条件,例如:

removingOnlyPosOdds :: Integral i => [[i]] -> [[i]]
removingOnlyPosOdds = filter (not . null) . map (filter (\x -> not (odd x && x > 0)))

或什至没有积分:

import Control.Monad(liftM2)

removingOnlyPosOdds :: Integral i => [[i]] -> [[i]]
removingOnlyPosOdds = filter (not . null) . map (filter (not . liftM2 (&&) odd (>0)))

例如:

Prelude> removingOnlyPosOdds [[-3],[-5,8],[1,3,5,7,9],[],[4,6,8,10],[1,3,6,7,9],[],[1]]
[[-3],[-5,8],[4,6,8,10],[6]]