2018-12-06 18:53:07 +00:00
|
|
|
from typing import Callable
|
|
|
|
|
2018-10-11 16:15:52 +00:00
|
|
|
import pytest # type: ignore
|
|
|
|
|
2018-10-12 21:02:17 +00:00
|
|
|
from monads import Monad
|
|
|
|
from .fixtures import monad
|
2018-10-11 16:15:52 +00:00
|
|
|
|
|
|
|
|
|
|
|
def test_bind(monad) -> None:
|
2018-10-12 01:06:23 +00:00
|
|
|
expected: Monad[int] = monad.pure(2)
|
|
|
|
assert expected == monad.pure(1).bind(lambda x: monad.pure(x + 1))
|
2018-10-11 16:15:52 +00:00
|
|
|
|
|
|
|
|
2018-12-06 18:53:07 +00:00
|
|
|
def test_bind_rshift_operator(monad) -> None:
|
|
|
|
m: Monad[int] = monad.pure(2)
|
|
|
|
f: Callable[[int], Monad[int]] = lambda x: monad.pure(x + 1)
|
|
|
|
assert m.bind(f) == m >> f
|
|
|
|
|
|
|
|
|
2018-10-11 16:15:52 +00:00
|
|
|
def test_left_identity(monad) -> None:
|
|
|
|
n: int = 3
|
|
|
|
|
|
|
|
def f(n: int) -> Monad[int]:
|
2018-10-12 01:06:23 +00:00
|
|
|
return monad.pure(n * 3)
|
2018-10-11 16:15:52 +00:00
|
|
|
|
2018-10-12 01:06:23 +00:00
|
|
|
assert monad.pure(n).bind(f) == f(n)
|
2018-10-11 16:15:52 +00:00
|
|
|
|
|
|
|
|
|
|
|
def test_right_identity(monad) -> None:
|
2018-10-12 01:06:23 +00:00
|
|
|
m: Monad[int] = monad.pure(3)
|
|
|
|
assert m == m.bind(lambda x: monad.pure(x))
|
2018-10-11 16:15:52 +00:00
|
|
|
|
|
|
|
|
|
|
|
def test_associativity(monad) -> None:
|
2018-10-12 01:06:23 +00:00
|
|
|
m: Monad[int] = monad.pure(3)
|
2018-10-11 16:15:52 +00:00
|
|
|
|
|
|
|
def f(n: int) -> Monad[int]:
|
2018-10-12 01:06:23 +00:00
|
|
|
return monad.pure(n * 3)
|
2018-10-11 16:15:52 +00:00
|
|
|
|
|
|
|
def g(n: int) -> Monad[int]:
|
2018-10-12 01:06:23 +00:00
|
|
|
return monad.pure(n + 5)
|
2018-10-11 16:15:52 +00:00
|
|
|
|
|
|
|
assert m.bind(f).bind(g) == m.bind(lambda x: f(x).bind(g))
|
2018-12-12 03:08:15 +00:00
|
|
|
|
|
|
|
|
|
|
|
def test_sequence(monad) -> None:
|
|
|
|
assert monad.pure([1, 2, 3]) == monad.sequence(
|
|
|
|
[monad.pure(1), monad.pure(2), monad.pure(3)]
|
|
|
|
)
|