use*_*277 3 polymorphism haskell functor
在我的项目中,我有一些看起来像这样的数据类型
data StructureA = StructureA [Int] Bool Int
data StructureB = StructureB [String] String
Run Code Online (Sandbox Code Playgroud)
我的目标是将函数映射到包含在此类数据类型的实例中的数组
inst = StructureA [1,1,1] True 0
fmap (+1) inst -- [2,2,2]
Run Code Online (Sandbox Code Playgroud)
我的初始解决方案解决方案如此
instance Functor StructureA where
fmap (StructureA arr _ _) = fmap arr
Run Code Online (Sandbox Code Playgroud)
但是,我得到了错误的错误.
问题是我如何声明一个可以多态应用于这些数据结构的函数?
您只能Functor通过参数化类型(* -> *确切地说)声明实例:仍需要额外(且恰好一个)类型参数的类型.
首先,我们需要引入一个类型参数.即使你从未计划使用除Ints 以外的其他东西,我们也可以轻松地将其抽象出来:
data Structure a = Structure [a] Bool IntRun Code Online (Sandbox Code Playgroud)
我们可以举例说明StructureA一个类型的同义词:
type StructureA = Structure IntRun Code Online (Sandbox Code Playgroud)
现在我们可以Functor通过写:
instance Functor Structure where
fmap f (Structure as b c) = ...Run Code Online (Sandbox Code Playgroud)
请注意,我们这里也没有写(Structure a),而是Structure因为-就像我们已经说过- fmap有充分的自由来改变在其收集的作品类型:该f功能可以具有例如类型Int -> Char的转换Structure Int到Structure Char.
现在我们仍然需要实施fmap.fmap具有类型fmap :: Functor f => (a -> b) -> f a -> f b,这意味着它需要一个函数,在这种情况下是一个Structure a,并构造一个Structure b.基于你的问题(以及我们做出的设计决策),我们可以映射的唯一部分是第一个参数,所以我们构造一个new Structure,其中第二个参数是a的结果fmap f,但是然后超过第二个参数,所以:
instance Functor Structure where
fmap f (Structure as b c) = Structure (fmap f as) b cRun Code Online (Sandbox Code Playgroud)