Skip to content

Instantly share code, notes, and snippets.

@SekiT
Created May 24, 2018 12:41
Show Gist options
  • Save SekiT/5ea45b975814f3c081905237cf364106 to your computer and use it in GitHub Desktop.
Save SekiT/5ea45b975814f3c081905237cf364106 to your computer and use it in GitHub Desktop.
defmodule ApplicativeMaybe do
@type t(a) :: {:just, a} | :nothing
@spec pure(val :: a) :: t(a) when a: var
def pure(val), do: {:just, val}
@spec fmap(f :: (a -> b), ma :: t(a)) :: t(b) when a: var, b: var
def fmap(f, {:just, val}), do: {:just, f.(val)}
def fmap(_, :nothing ), do: :nothing
@spec ap(mf :: t((a -> b)), ma :: t(a)) :: t(b) when a: var, b: var
def ap({:just, f}, {:just, val}), do: {:just, f.(val)}
def ap(_ , _ ), do: :nothing
end
alias ApplicativeMaybe, as: M
f = fn a -> fn b -> fn c -> fn d -> %{ab: a + b, cd: c <> d} end end end end
f |> M.fmap(M.pure(2)) |> M.ap(M.pure(3)) |> M.ap(M.pure("foo")) |> M.ap(M.pure("bar"))
# => {:just, %{ab: 5, cd: "foobar"}}
f |> M.fmap(M.pure(2)) |> M.ap(M.pure(3)) |> M.ap(:nothing) |> M.ap(M.pure("bar"))
# => :nothing
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment