【问题标题】:how to split a list into two odd and even lists in haskell using splitWhen function and predicate function如何使用 splitWhen 函数和谓词函数在haskell中将列表拆分为两个奇数和偶数列表
【发布时间】:2014-12-30 23:23:47
【问题描述】:

我是 Haskell 的新手,我想根据条件拆分列表,如果列表的元素是偶数还是奇数,使用 splitWhen 函数将第一个参数作为布尔条件。这个布尔条件是另一个名为 checkEven 的函数的返回。但是我怎样才能将元素传递给 checkEven 函数。这甚至可能吗?

checkEven n=(n mod 2==0)
splitList x= splitWhen (checkEven(<???>)) x
main =do 
 print (splitList [0,1,2,3,-1])

如果上述方法错误,请提出其他解决此问题的方法。但我也遇到了同样的问题。

提前致谢

【问题讨论】:

标签: haskell functional-programming


【解决方案1】:

不,splitWhen 不能为您执行此操作,因为它会丢弃分隔符,并且您需要保留所有输入数据:

splitWhen checkEven [1,2,3,4,6,8,9,10] == [[1],[3],[],[],[9],[]]

您可以使用 Data.List.Split 库来执行此操作,因为它非常灵活。 只要元素是偶数,我们就可以拆分,所以我们使用whenElt even

ghci> :m Data.List.Split
ghci> split (whenElt even) [1,11,2,22,3,33,333,4,6,8,9,99,999,10,100]
[[1,11],[2],[],[22],[3,33,333],[4],[],[6],[],[8],[9,99,999],[10],[],[100],[]]

但我们希望将多个分隔符(如 2,22)压缩到一个列表中,而不是像我们那样在其间有一个空的奇数列表,因此我们使用 condense 修饰符:

ghci> split (condense $ whenElt even) [1,11,2,22,3,33,333,4,6,8,9,99,999,10,100]
[[1,11],[2,22],[3,33,333],[4,6,8],[9,99,999],[10,100],[]]

但是让我们放弃最后出现的空白列表,因为最后还有另一个空的赔率列表:

ghci> split (dropFinalBlank . condense $ whenElt even) [1,11,2,22,3,33,333,4,6,8,9,99,999,10,100]
[[1,11],[2,22],[3,33,333],[4,6,8],[9,99,999],[10,100]]

另一方面,如果您是从头开始实现此功能,则需要使用 break 函数。

【讨论】:

    【解决方案2】:

    感谢@AndrewC 的回答。我很困惑如何拆分列表并尝试使用内置的 splitWhen 函数。但实际上我找到了不使用 splitWhen 函数而是使用前奏函数的解决方案。

    splitOE::[Integer]->(Integer->Bool)->([Integer],[Integer])
    nums=[1,3,5,2,6,7,12,14,9]
    splitOE xs preFunc=(a,b)
            where a=[x|x<-xs,preFunc x]
                  b=[x|x<-xs,(not.preFunc) x]
    main = do 
            print (splitOE nums even)
    *Main> main
    ([2,6,12,14],[1,3,5,7,9])
    

    这解决了我的问题,虽然不是我在问题中提出的问题

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-12-18
      • 1970-01-01
      • 1970-01-01
      • 2019-10-27
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多