Dear Java guy, State is a monad

interface Pair<A, B> {
  A first();
  B second();
}
 
class Pairs {
  public static <A, B> Pair<A, B> pair(final A a, final B b) {
    return new Pair<A, B>() {
      public A first() { return a; }
      public B second() { return b; }
    };
  }
}
 
interface State<S, A> {
  Pair<S, A> run(S s);
}
 
interface Function<X, Y> {
  Y apply(X x);
}
 
class States {
  // State<S, _> is a covariant functor
  public static <S, A, B> State<S, B> map(final State<S, A> s, final Function<A, B> f) {
    return new State<S, B>() {
      public Pair<S, B> run(final S k) {
        final Pair<S, A> p = s.run(k);
        return Pairs.pair(p.first(), f.apply(p.second()));
      }
    };
  }
 
  // // State<S, _> is a monad
  public static <S, A, B> State<S, B> bind(final State<S, A> s, final Function<A, State<S, B>> f) {
    return new State<S, B>() {
      public Pair<S, B> run(final S k) {
        final Pair<S, A> p = s.run(k);
        return f.apply(p.second()).run(p.first());
      }
    };
  }
}

5 Responses to “Dear Java guy, State is a monad”

  1. Steven Shaw Says:

    Tony, I’m struggling to see how to use this thing. Can see how the S threads through but what is a good type for S?

    http://github.com/steshaw/playground/blob/master/java/state-is-a-monad/StateMonadExample.java

    a Java guy

  2. Tony Morris Says:

    Hi mate,
    Consider that State is a function: S -> (S, A). I have given examples on here before in other languages: http://blog.tmorris.net/the-state-monad-for-scala-users/

    Consider that there exists a function: (S -> S) -> A -> State<S, A> then think of all the possibilities for the first argument, then try to use the resulting function. e.g. suppose +1, then you have a function A -> State<Int, A> which is the same as A -> Int -> (Int, A) which is isomorphic (by curry/uncurry and flip) to (Int, A) -> (Int, A).

    Is this a useful function? It looks like a loop that computes values while implicitly adding the value 1 as it recurses don’t you think? Try to use it for something useful.

  3. John Nilsson Says:

    I’m struggling to see _why_ to use this thing.
    Honestly, if there is a reason I’d like to know.

    In essence my question is, when is this better than using Javas native support for state? Like the comment in the Scala example you linked to.

  4. Tony Morris Says:

    Hello John,
    I hope to partially answer that question when I get a chance in another post. Specifically, the question Why Does Monad Matter?

    All I wanted to do here is witness that State (with a universally quantified type variable) is itself a monad.

  5. Marco Faustinelli Says:

    Good morning Tony. Actually I believe me and many others would appreciate to read a specific answer to the specific question from John Nilsson. Why/when is this better than Java’s language-specific state support? I already know a monad is a fluffy cloud, but generic messages like these don’t actually increase my sense of urgency about learning and applying in my day job such a complex matter.
    Thanks in advance and have a nice day,
    Marco

Leave a Reply