Current section
Files
Jump to
Current section
Files
lib/monoid.ex
defprotocol Monoid do
@moduledoc """
Monoids extend semigroups, objects with an associative binary operator, by adding the notion of
an identity element.
Given the `mcat` operator as `⋅`, monoids must satisfy:
∀ a. identity ⋅ a = a ⋅ identity = a
∀ a b c. a ⋅ (b ⋅ c) = (a ⋅ b) ⋅ c
## Built-in instances
Built in instances are defined for `List`, `Map`, and `Stream`. For example:
iex> Monoid.mplus([1, 2], [3, 4])
[1, 2, 3, 4]
iex> Monoid.identity([1, 2, 3])
[]
iex> Monoid.identity(%{foo: :bar})
%{}
"""
@doc """
The associative binary operator over objects of this monoidal category
"""
@spec mplus(Monoid.t, Monoid.t) :: Monoid.t
def mplus(x, y)
@doc """
The left and right identity of `mplus`
"""
@spec identity(Monoid.t) :: Monoid.t
def identity(x)
end
defimpl Monoid, for: List do
def mplus(x, y), do: x ++ y
def identity(_), do: []
end
defimpl Monoid, for: Map do
defdelegate mplus(x, y), to: Map, as: :merge
def identity(_), do: %{}
end