我制作了一个用于测试 fclabel 的最小示例。使用镜头从 Either 值中检索“正确”值。为什么会失败?我错过了什么吗?
module Label where
import Data.Label
import Data.Label.Base
test = get right (Right "test")
{- Will fail with this message:
Label.hs:5:12:
No instance for (Control.Arrow.ArrowZero Data.Label.Point.Total)
arising from a use of `right'
Possible fix:
add an instance declaration for
(Control.Arrow.ArrowZero Data.Label.Point.Total)
In the first argument of `get', namely `right'
In the expression: get right (Right "test")
In an equation for `test': test = get right (Right "test")
Failed, modules loaded: none.
-- Tested with fclabels-2.0.2
-}
最佳答案
这个错误相当晦涩,但是当我们查看 get
的类型和文档时,它会变得更加清晰。和 right
:
get :: (f :-> a) -> f -> a
type :-> f o = Lens Total f o
right :: (ArrowZero arr, ArrowApply arr, ArrowChoice arr)
=> Lens arr (Either a b -> Either a o) (b -> o)
-- Lens pointing to the right value in an Either. (Partial and polymorphic)
本质上,您使用的get
仅适用于总镜头,但right
不是总镜头,因为它不会如果值为 Left
,则有效。该错误表示部分镜头要求载体类型为 ArrowZero
,但总镜头无法做到这一点。
如果您在 ghci
中进行实验,只需调用 get right
(不带任何参数)就会出现此错误。
如果将 Data.Label
的导入更改为 Data.Label.Partial
,那么你的代码就可以工作了。 test
最终得到类型 Maybe String
。
关于haskell - 使用 fclabel 中的 'left' 镜头时出现类型错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26370141/