将Eithers列表转换为包含列表的Either

时间:2016-07-02 22:32:56

标签: haskell

我是Haskell的初学者,我正在研究一些使用Either进行错误处理的Haskell代码。 Either的左侧元素表示错误,而右侧元素表示成功结果。代码经常使用Either的Applicative实例,它似乎是为这个用例设计的。

给定[Either e r]类型的对象,将它转换为Either e [r]类型的对象的最优雅方法是什么?这一点的意思是我们可能有一些来自我们调用的函数的返回值数组,如果这些返回值中的任何一个是错误,我们希望得到该错误并抛弃其他所有内容。如果数组的多个元素有错误,我希望尽可能得到最左边的错误。

我能够通过编写两个函数自己在下面的代码中解决这个问题,其中一个是递归的,但是有更好的方法吗?

type Error = [Char]

myFunc :: [Either Error a] -> Either Error [a]
myFunc = myFunc2 []

myFunc2 :: [a] -> [Either Error a] -> Either Error [a]
myFunc2 r ((Left error):rest) = Left error
myFunc2 r ((Right item):rest) = myFunc2 (r ++ [item]) rest
myFunc2 r [] = Right r

main :: IO()
main = do
  -- This prints: Right [1, 2, 3]
  putStrLn (show (myFunc [Right 1, Right 2, Right 3]))

  -- This prints: Left "division by zero"
  putStrLn (show (myFunc [Right 1, Left "division by zero", Right 3]))

2 个答案:

答案 0 :(得分:14)

来自 $kitchenKeys = "{'Kithcen1'}"; var_dump($f[$kitchenKeys]); Output: NULL $dishKeys = "{'Kitchen'}][{'Dishes'}"; var_dump($f[$dishKeys]); Output: NULL $ironKeys = "{'Kitchen1'}][{'Blue things One'}][{'Iron'}"; var_dump($f[$ironKeys]); Output: NULL

sequence

Control.Monad

如:

sequence :: (Traversable t, Monad m) => t (m a) -> m (t a)

答案 1 :(得分:9)