Skip to content

Instantly share code, notes, and snippets.

@puffnfresh
Last active January 7, 2024 10:17
Show Gist options
  • Star 6 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save puffnfresh/6161753 to your computer and use it in GitHub Desktop.
Save puffnfresh/6161753 to your computer and use it in GitHub Desktop.
Monoid trait and implementations in Rust
trait Semigroup {
fn mappend(&self, b: Self) -> Self;
}
trait Monoid: Semigroup {
fn mempty() -> Self;
}
impl Semigroup for int {
fn mappend(&self, b: int) -> int { *self + b }
}
impl Monoid for int {
fn mempty() -> int { 0 }
}
impl Semigroup for ~str {
fn mappend(&self, b: ~str) -> ~str { *self + b }
}
impl Monoid for ~str {
fn mempty() -> ~str { ~"" }
}
fn main() {
println((~"Hello").mappend(~"World").to_str());
println(1.mappend(2).to_str());
// `as` didn't work as ascription.
let str_zero: ~str = Monoid::mempty();
let int_zero: int = Monoid::mempty();
println(str_zero);
println(int_zero.to_str());
}
@vi
Copy link

vi commented Sep 22, 2015

"Monoid" trait seems to be equvivalent to Default trait. I can't find something like this for "Semigroup" although.

Update: found the difference: Monoid: Semigroup.

@cblp
Copy link

cblp commented Jul 19, 2016

@vi Monoid is not equivalent to Default.

Monoid must satisfy specific laws:

  1. a.mappend(mempty()) == a
  2. mempty.mappend(a) == a

Default mustn't.

Default may make sense without Semigroup, Monoid doesn't.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment