了解具有可折叠的单形容器

时间:2017-11-24 13:38:01

标签: haskell

snoyberg/mono-traversable' README笔记

  

[MonoFoldable与Foldable相同],但也可以在单形容器上运行。

请举例说明Foldable不能在单态容器上运行。

4 个答案:

答案 0 :(得分:6)

Text直观地是一个容器,但它不是多态的。因此

Prelude> Data.Foldable.foldr ((:) . fromEnum) [] (Data.Text.pack "blub")

<interactive>:8:28: error:
    • Couldn't match expected type ‘[a0]’
                  with actual type ‘Data.Text.Internal.Text’
    • In the third argument of ‘foldr’, namely
        ‘(Data.Text.pack "blub")’
      In the expression:
        foldr ((:) . fromEnum) [] (Data.Text.pack "blub")
      In an equation for ‘it’:
          it = foldr ((:) . fromEnum) [] (Data.Text.pack "blub")

OTOH,

Prelude> Data.MonoTraversable.ofoldr ((:) . fromEnum) [] (Data.Text.pack "blub")
[98,108,117,98]

答案 1 :(得分:4)

Foldable* -> *种。列表,树,基本上任何可以为其元素类型采用其他类型的东西都具有这种类型。 Foldable的任何实例必须是类型构造函数,而不是类型,因为该类定义为

class Foldable (t :: * -> *) where
   foldMap :: Monoid m => (a -> m) -> t a -> m
                                  --  ^ ^

但是,TextByteString和其他类型显然是某些基础元素类型的集合,但它们的类型是*。它们不是类型构造函数,它们已经是类型。它们不适合foldMap的类型:

listLength :: Text -> Int
listLength = getSum . foldMap (const (Sum 1))

textLength :: Text -> Int
textLength = foldMap magic -- will never compile, for no magic

答案 2 :(得分:1)

我认为这里的意思是,通常在谈论Foldable时,我们指的是更高级别的多态版本。即对于所有ListFoldablea。因此Foldable适用于类型* - &gt; *(也称为类型构造函数)。

MonoFoldable类型类适用于实际类型。因此,例如,我们可以为MonoFoldable

之类的内容编写Text的实例

答案 3 :(得分:1)

ByteStringText,分别只能包含Word8Char。另外unboxed arrays对其数据类型有限制,因此无法直接创建Foldable的实例。

但是请注意,只需将Monofoldable恰当地包装成Foldable即可。我的包make-monofoldable-foldable会为您执行此操作,例如,如果您需要将ByteString传递给期望Foldable的函数,则可以使用WrappedMonoFoldable将其包装,然后传递它。