diff --git a/src/Ord.ts b/src/Ord.ts index 38ab57c7b..3a24dcbe8 100644 --- a/src/Ord.ts +++ b/src/Ord.ts @@ -16,6 +16,7 @@ import { Semigroup } from './Semigroup' import { Eq } from './Eq' import { Contravariant1 } from './Contravariant' import { pipeable } from './pipeable' +import { Monoid } from './Monoid' declare module './HKT' { interface URItoKind { @@ -226,6 +227,18 @@ export function getSemigroup(): Semigroup> { } } +const empty = fromCompare(() => 0) + +/** + * @since 2.4.0 + */ +export function getMonoid(): Monoid> { + return { + empty, + concat: getSemigroup().concat + } +} + /** * Given a tuple of `Ord`s returns an `Ord` for the tuple * diff --git a/test/Ord.ts b/test/Ord.ts index 78b520eec..fe8d4e56f 100644 --- a/test/Ord.ts +++ b/test/Ord.ts @@ -6,6 +6,7 @@ import { clamp, getDualOrd, getSemigroup, + getMonoid, ordDate, ordNumber, ordString, @@ -15,6 +16,7 @@ import { getTupleOrd, ordBoolean } from '../src/Ord' +import { fold } from '../src/Monoid' describe('Ord', () => { it('getTupleOrd', () => { @@ -51,6 +53,33 @@ describe('Ord', () => { ]) }) + it('getMonoid', () => { + interface Person { + name: string + age: number + } + const people: Person[] = [ + { name: 'John', age: 42 }, + { name: 'Dorothy', age: 37 }, + { name: 'John', age: 37 } + ] + + const sortByName = ord.contramap(ordString, (p: Person) => p.name) + const sortByAge = ord.contramap(ordNumber, (p: Person) => p.age) + + const monoid = getMonoid() + const sortByNameByAge = fold(monoid)([sortByName, sortByAge]) + const dontSort = fold(monoid)([]) + + assert.deepStrictEqual(sort(sortByNameByAge)(people), [ + { name: 'Dorothy', age: 37 }, + { name: 'John', age: 37 }, + { name: 'John', age: 42 } + ]) + + assert.deepStrictEqual(sort(dontSort)(people), people) + }) + it('ordNumber', () => { assert.strictEqual(ordNumber.compare(1, 2), -1) assert.strictEqual(ordNumber.compare(2, 1), 1)