问题描述
好像我很清楚地了解Haskell中的Monoid
是什么,但是上次我听说了一个称为免费类半身像的东西.
Looks like I have a pretty clear understanding what a Monoid
is in Haskell, but last time I heard about something called a free monoid.
什么是免费的半身像,它与一个半身像有什么关系?
What is a free monoid and how does it relate to a monoid?
您可以在Haskell中提供示例吗?
Can you provide an example in Haskell?
推荐答案
在编程环境中,我通常将 free monoid 转换为[a]
.在有关针对程序员的类别理论的精彩文章系列中,,Bartosz Milewski将Haskell中的免费类人动物描述为列表类人(假设有人忽略了无限列表的某些问题.
In a programming context, I usually translate free monoid to [a]
. In his excellent series of articles about category theory for programmers, Bartosz Milewski describes free monoids in Haskell as the list monoid (assuming one ignores some problems with infinite lists).
identity元素为空列表,二进制操作为列表串联:
The identity element is the empty list, and the binary operation is list concatenation:
Prelude Data.Monoid> mempty :: [Int]
[]
Prelude Data.Monoid> [1..3] <> [7..10]
[1,2,3,7,8,9,10]
直觉上,我认为此monoid是免费的",因为无论您要使用哪种价值类型,您都可以始终应用此monoid(就像免费monad是您可以始终从任何仿函数创建的一个monad.
Intuitively, I think of this monoid to be 'free' because it a monoid that you can always apply, regardless of the type of value you want to work with (just like the free monad is a monad you can always create from any functor).
另外,当一个类型存在一个以上的monoid时,自由的monoid将推迟使用哪个特定的monoid的决定.例如,对于整数,存在无限多的类四面体,但最常见的是加法和乘法.
Additionally, when more than one monoid exists for a type, the free monoid defers the decision on which specific monoid to use. For example, for integers, infinitely many monoids exist, but the most common are addition and multiplication.
如果您有两个(或更多的整数),并且知道您可能希望对其进行汇总,但尚未决定要应用哪种汇总类型,则可以使用免费的汇总"它们monoid-实际上,这意味着将它们放在列表中:
If you have two (or more integers), and you know that you may want to aggregate them, but you haven't yet decided which type of aggregation you want to apply, you can instead 'aggregate' them using the free monoid - practically, this means putting them in a list:
Prelude Data.Monoid> [3,7]
[3,7]
如果您以后决定要将它们添加在一起,则可以:
If you later decide that you want to add them together, then that's possible:
Prelude Data.Monoid> getSum $ mconcat $ Sum <$> [3,7]
10
相反,如果您希望将它们相乘,也可以这样做:
If, instead, you wish to multiply them, you can do that as well:
Prelude Data.Monoid> getProduct $ mconcat $ Product <$> [3,7]
21
在这两个示例中,我故意选择将每个数字提升为包含更具体的类半体动物的类型(Sum
,Product
),然后使用mconcat
进行聚合.
In these two examples, I've deliberately chosen to elevate each number to a type (Sum
, Product
) that embodies a more specific monoid, and then use mconcat
to perform the aggregation.
对于加法和乘法,有更多简洁的方法可以做到这一点,但是我这样做是为了说明如何使用更具体的monoid来解释自由monoid.
For addition and multiplication, there are more succinct ways to do this, but I did it that way to illustrate how you can use a more specific monoid to interpret the free monoid.
这篇关于Free Monoid和Monoid之间的主要区别是什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!