12
12
import static com .jnape .palatable .lambda .adt .Maybe .nothing ;
13
13
import static com .jnape .palatable .lambda .functions .builtin .fn1 .Constantly .constantly ;
14
14
import static com .jnape .palatable .lambda .functions .builtin .fn1 .Id .id ;
15
+ import static com .jnape .palatable .lambda .functions .builtin .fn1 .Upcast .upcast ;
16
+ import static com .jnape .palatable .lambda .monad .Monad .join ;
15
17
import static java .util .Arrays .asList ;
16
18
17
19
public class MonadLaws <M extends Monad > implements Trait <Monad <?, M >> {
@@ -22,7 +24,8 @@ public void test(Monad<?, M> m) {
22
24
.<Function <Monad <?, M >, Maybe <String >>>foldMap (f -> f .apply (m ), asList (
23
25
this ::testLeftIdentity ,
24
26
this ::testRightIdentity ,
25
- this ::testAssociativity ))
27
+ this ::testAssociativity ,
28
+ this ::testJoin ))
26
29
.peek (s -> {
27
30
throw new AssertionError ("The following Monad laws did not hold for instance of " + m .getClass () + ": \n \t - " + s );
28
31
});
@@ -32,21 +35,29 @@ private Maybe<String> testLeftIdentity(Monad<?, M> m) {
32
35
Object a = new Object ();
33
36
Fn1 <Object , Monad <Object , M >> fn = id ().andThen (m ::pure );
34
37
return m .pure (a ).flatMap (fn ).equals (fn .apply (a ))
35
- ? nothing ()
36
- : just ("left identity (m.pure(a).flatMap(fn).equals(fn.apply(a)))" );
38
+ ? nothing ()
39
+ : just ("left identity (m.pure(a).flatMap(fn).equals(fn.apply(a)))" );
37
40
}
38
41
39
42
private Maybe <String > testRightIdentity (Monad <?, M > m ) {
40
43
return m .flatMap (m ::pure ).equals (m )
41
- ? nothing ()
42
- : just ("right identity: (m.flatMap(m::pure).equals(m))" );
44
+ ? nothing ()
45
+ : just ("right identity: (m.flatMap(m::pure).equals(m))" );
43
46
}
44
47
45
48
private Maybe <String > testAssociativity (Monad <?, M > m ) {
46
49
Fn1 <Object , Monad <Object , M >> f = constantly (m .pure (new Object ()));
47
50
Function <Object , Monad <Object , M >> g = constantly (m .pure (new Object ()));
48
51
return m .flatMap (f ).flatMap (g ).equals (m .flatMap (a -> f .apply (a ).flatMap (g )))
49
- ? nothing ()
50
- : just ("associativity: (m.flatMap(f).flatMap(g).equals(m.flatMap(a -> f.apply(a).flatMap(g))))" );
52
+ ? nothing ()
53
+ : just ("associativity: (m.flatMap(f).flatMap(g).equals(m.flatMap(a -> f.apply(a).flatMap(g))))" );
54
+ }
55
+
56
+ private Maybe <String > testJoin (Monad <?, M > m ) {
57
+ Monad <Monad <Object , M >, M > mma = m .pure (m .fmap (upcast ()));
58
+ boolean equals = mma .flatMap (id ()).equals (join (mma ));
59
+ return equals
60
+ ? nothing ()
61
+ : just ("join: (m.pure(m).flatMap(id())).equals(Monad.join(m.pure(m)))" );
51
62
}
52
63
}
0 commit comments