我有一个跟踪数字“块”的数据类型(有点像矩阵)。
newtype Block a = Block [[a]]
我想让它成为
Functor
的一个实例.但是,我试图以 fmap 可以应用于整个列表块的方式来执行此操作,以便 fmap 具有类型 fmap :: [[a]] -> [[b]]
而不是类型 fmap :: a -> b
.原因是因为我想映射到我的
Block
仿函数如 transpose
适用于列表块 [[a]]
不是每个元素a
.也就是说,我希望能够定义像transposeBlock :: Block a -> Block a
transposeBlock = (transpose <$>)
我试图将我的仿函数实例声明如下。
instance Functor (Block [[a]]) where
fmap f (Block x) = Block (f x)
但是我遇到了尝试编译它时出现的类型错误。
error:
• Expecting one fewer argument to ‘Block [[a]]’
Expected kind ‘* -> *’, but ‘Block [[a]]’ has kind ‘*’
• In the first argument of ‘Functor’, namely ‘Block [[a]]’
In the instance declaration for ‘Functor (Block [[a]])’
有哪些方法可以将函数映射到列表块
[[a]]
我的 Block
类型?
最佳答案
抱歉,您不能调用该函数 fmap
.但没关系,还有很多其他好名字。
onBlock :: ([[a]] -> [[b]]) -> Block a -> Block b
onBlock f (Block v) = Block (f v)
如果你愿意,你甚至可以给它起一个充满不确定标点符号的名字。
(<#>) :: ([[a]] -> [[b]]) -> Block a -> Block b
f <#> Block v = Block (f v)
关于haskell - fmap 应用于类型变量以外的类型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47703453/