public static <A> Ord<List<A>> listOrd(final Ord<A> oa) {
    return ord(l1 -> l2 -> {
        if (l1.isEmpty())
            return l2.isEmpty() ? Ordering.EQ : Ordering.LT;
        else if (l2.isEmpty())
            return l1.isEmpty() ? Ordering.EQ : Ordering.GT;
        else {
            final Ordering c = oa.compare(l1.head(), l2.head());
            return c == Ordering.EQ ? listOrd(oa).f.f(l1.tail()).f(l2.tail()) : c;
        }
    });
  }