【问题标题】:Haskell creating my own filtering functionHaskell 创建我自己的过滤功能
【发布时间】:2016-01-28 17:48:11
【问题描述】:

我是 haskell 的新手,我正在尝试创建一个函数,该函数将获取整数列表并返回包含两个子列表的列表,第一个子列表包含偶数,另一个包含奇数。我不能使用偶数、奇数或过滤函数。我创建了自己的函数如下

myodd :: Integer -> Bool
myodd n = rem (abs(n)) 2 == 1

myeven :: Integer -> Bool
myeven n = rem (abs(n)) 2 == 0

segregate [] = ([], [])
segregate [x] = ([x], [])
segregate (x:y:xs) = (x:xp, y:yp) where (xp, yp) = segregate xs

我在尝试使用前两个函数并将其用于隔离函数时遇到了麻烦。我在球拍方面有更多经验,我创建的功能如下所示:

    (define (myeven? x)
  (= (modulo x 2) 0)) 

(define (myodd? x)
  (= (modulo x 2) 1))

(define (segregate xs)
  (foldr (lambda (x b)
           (if (myeven? x)
               (list (cons x (first b)) (second b))
               (list (first b) (cons x (second b))))) '(()()) xs))

【问题讨论】:

  • 您的球拍代码没有意义。你测试过吗?
  • 对我来说,看起来你的 Haskell 代码和你的 Racket 代码正在做两件非常不同的事情 - Racket 代码根据 value 是奇数还是奇数来划分输入列表偶数,而 Haskell 代码根据值的 index 是奇数还是偶数来划分输入列表(尽管代码中存在错误)。您实际上想要实现这两者中的哪一个?
  • @FrankSchmitt,Racket 代码实际上似乎并没有这样做。事实上,我很确定它也会抛出错误。
  • @dfeuer 这就是为什么我写了“尽管代码中有错误”——对我来说,看起来代码应该按照我的描述进行(我可能弄错了,当然)。
  • 很抱歉我发布了错误的代码。我刚刚修复了 (define (myeven?x) (= (modulo x 2) 0)) (define (myodd?x) (= (modulo x 2) 1)) (define (segregate xs) (foldr (lambda (xb) (if (myeven?x) (list (cons x (first b)) (second b)) (list (first b) (cons x (second b))))) '(()()) xs))

标签: haskell functional-programming


【解决方案1】:

这是一种好方法:

segregate [] = ?
segregate (x:xs)
  | myEven x = ?
  | otherwise = ?
  where (restEvens, restOdds) = segregate xs

你也可以使用

segregate = foldr go ([], []) where
  go x ~(evens, odds)
    | myEven x = ?
    | otherwise = ?

【讨论】:

    【解决方案2】:

    一种简单的方法是使用您的每个手动函数作为保护谓词,遍历列表两次:

    segregate :: [Integer] -> ([Integer], [Integer])
    segregate [] = ([],[])
    segregate xs = (evens, odds)
      where evens = [x | x <- xs, myeven x]
            odds  = [x | x <- xs, myodd x]
    

    注意:您的问题要求提供列表列表,但您的模式匹配 segregate [] = ([],[]) 表明您想要一个元组,所以我提供了一个元组解决方案。

    【讨论】:

    • 感谢您的回复。我在编译代码时遇到了一些问题。它给出了如下编译错误: 无法将预期类型 'Bool' 与实际类型 'Integer -> Bool' 匹配 可能的原因:'myodd' 应用于太少的参数 在表达式中:myodd 在列表理解的一个 stmt : 奇怪
    【解决方案3】:

    如果你真的需要这样的函数而不是为了教育目的而编写它,Data.List中有partition,所以很简单

    import Data.List(partition) 
    

    会带你去的。

    在教育案例中,您仍然可以在完成后将您的代码与partition 的代码进行比较。

    【讨论】:

      猜你喜欢
      • 2012-04-08
      • 1970-01-01
      • 2013-07-04
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-09-20
      • 2013-04-29
      相关资源
      最近更新 更多