Skip to content

Commit 3afdabc

Browse files
committed
- Adding MonadRec instance for remaining monads
- Better documentation
1 parent ad16a75 commit 3afdabc

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

54 files changed

+729
-253
lines changed

src/main/java/com/jnape/palatable/lambda/adt/Try.java

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
import com.jnape.palatable.lambda.adt.coproduct.CoProduct2;
44
import com.jnape.palatable.lambda.functions.Fn0;
55
import com.jnape.palatable.lambda.functions.Fn1;
6+
import com.jnape.palatable.lambda.functions.recursion.RecursiveResult;
67
import com.jnape.palatable.lambda.functions.builtin.fn1.Downcast;
78
import com.jnape.palatable.lambda.functions.specialized.Pure;
89
import com.jnape.palatable.lambda.functions.specialized.SideEffect;
@@ -11,6 +12,7 @@
1112
import com.jnape.palatable.lambda.io.IO;
1213
import com.jnape.palatable.lambda.monad.Monad;
1314
import com.jnape.palatable.lambda.monad.MonadError;
15+
import com.jnape.palatable.lambda.monad.MonadRec;
1416
import com.jnape.palatable.lambda.traversable.Traversable;
1517

1618
import java.util.Objects;
@@ -20,6 +22,8 @@
2022
import static com.jnape.palatable.lambda.functions.builtin.fn1.Constantly.constantly;
2123
import static com.jnape.palatable.lambda.functions.builtin.fn1.Id.id;
2224
import static com.jnape.palatable.lambda.functions.builtin.fn1.Upcast.upcast;
25+
import static com.jnape.palatable.lambda.functions.recursion.RecursiveResult.terminate;
26+
import static com.jnape.palatable.lambda.functions.recursion.Trampoline.trampoline;
2327
import static com.jnape.palatable.lambda.functor.builtin.Lazy.lazy;
2428
import static com.jnape.palatable.lambda.internal.Runtime.throwChecked;
2529

@@ -32,6 +36,7 @@
3236
*/
3337
public abstract class Try<A> implements
3438
MonadError<Throwable, A, Try<?>>,
39+
MonadRec<A, Try<?>>,
3540
Traversable<A, Try<?>>,
3641
CoProduct2<Throwable, A, Try<A>> {
3742

@@ -239,6 +244,17 @@ public <B> Try<A> discardR(Applicative<B, Try<?>> appB) {
239244
return MonadError.super.discardR(appB).coerce();
240245
}
241246

247+
/**
248+
* {@inheritDoc}
249+
*/
250+
@Override
251+
public <B> Try<B> trampolineM(Fn1<? super A, ? extends MonadRec<RecursiveResult<A, B>, Try<?>>> fn) {
252+
return flatMap(trampoline(a -> fn.apply(a).<Try<RecursiveResult<A, B>>>coerce().match(
253+
t -> terminate(failure(t)),
254+
aOrB -> aOrB.fmap(Try::success)
255+
)));
256+
}
257+
242258
/**
243259
* {@inheritDoc}
244260
*/

src/main/java/com/jnape/palatable/lambda/adt/choice/Choice2.java

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -150,13 +150,15 @@ public final <C> Choice2<A, C> flatMap(Fn1<? super B, ? extends Monad<C, Choice2
150150
return match(Choice2::a, b -> f.apply(b).coerce());
151151
}
152152

153+
/**
154+
* {@inheritDoc}
155+
*/
153156
@Override
154157
public <C> Choice2<A, C> trampolineM(Fn1<? super B, ? extends MonadRec<RecursiveResult<B, C>, Choice2<A, ?>>> fn) {
155158
return match(Choice2::a,
156-
trampoline(b -> fn.apply(b)
157-
.<Choice2<A, RecursiveResult<B, C>>>coerce()
158-
.match(a -> terminate(a(a)),
159-
bOrC -> bOrC.fmap(Choice2::b))));
159+
trampoline(b -> fn.apply(b).<Choice2<A, RecursiveResult<B, C>>>coerce()
160+
.match(a -> terminate(a(a)),
161+
bOrC -> bOrC.fmap(Choice2::b))));
160162
}
161163

162164
/**

src/main/java/com/jnape/palatable/lambda/adt/choice/Choice3.java

Lines changed: 12 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -39,17 +39,6 @@ public abstract class Choice3<A, B, C> implements
3939
Traversable<C, Choice3<A, B, ?>>,
4040
MonadRec<C, Choice3<A, B, ?>> {
4141

42-
/**
43-
* {@inheritDoc}
44-
*/
45-
@Override
46-
public <D> Choice3<A, B, D> trampolineM(Fn1<? super C, ? extends MonadRec<RecursiveResult<C, D>, Choice3<A, B, ?>>> fn) {
47-
return flatMap(trampoline(c -> fn.apply(c).<Choice3<A, B, RecursiveResult<C, D>>>coerce()
48-
.match(a -> terminate(a(a)),
49-
b -> terminate(b(b)),
50-
r -> r.fmap(Choice3::c))));
51-
}
52-
5342
private Choice3() {
5443
}
5544

@@ -163,6 +152,18 @@ public <D> Choice3<A, B, D> flatMap(Fn1<? super C, ? extends Monad<D, Choice3<A,
163152
return match(Choice3::a, Choice3::b, c -> f.apply(c).coerce());
164153
}
165154

155+
/**
156+
* {@inheritDoc}
157+
*/
158+
@Override
159+
public <D> Choice3<A, B, D> trampolineM(
160+
Fn1<? super C, ? extends MonadRec<RecursiveResult<C, D>, Choice3<A, B, ?>>> fn) {
161+
return flatMap(trampoline(c -> fn.apply(c).<Choice3<A, B, RecursiveResult<C, D>>>coerce()
162+
.match(a -> terminate(a(a)),
163+
b -> terminate(b(b)),
164+
r -> r.fmap(Choice3::c))));
165+
}
166+
166167
/**
167168
* {@inheritDoc}
168169
*/

src/main/java/com/jnape/palatable/lambda/adt/choice/Choice4.java

Lines changed: 14 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -154,17 +154,6 @@ public <E> Choice4<A, B, C, E> flatMap(Fn1<? super D, ? extends Monad<E, Choice4
154154
/**
155155
* {@inheritDoc}
156156
*/
157-
@Override
158-
@SuppressWarnings("unchecked")
159-
public <E, App extends Applicative<?, App>, TravB extends Traversable<E, Choice4<A, B, C, ?>>,
160-
AppTrav extends Applicative<TravB, App>> AppTrav traverse(Fn1<? super D, ? extends Applicative<E, App>> fn,
161-
Fn1<? super TravB, ? extends AppTrav> pure) {
162-
return match(a -> pure.apply((TravB) Choice4.<A, B, C, E>a(a)).coerce(),
163-
b -> pure.apply((TravB) Choice4.<A, B, C, E>b(b)).coerce(),
164-
c -> pure.apply((TravB) Choice4.<A, B, C, E>c(c)),
165-
d -> fn.apply(d).<Choice4<A, B, C, E>>fmap(Choice4::d).<TravB>fmap(Functor::coerce).coerce());
166-
}
167-
168157
@Override
169158
public <E> Choice4<A, B, C, E> trampolineM(
170159
Fn1<? super D, ? extends MonadRec<RecursiveResult<D, E>, Choice4<A, B, C, ?>>> fn) {
@@ -178,6 +167,20 @@ public <E> Choice4<A, B, C, E> trampolineM(
178167
dOrE -> dOrE.fmap(Choice4::d))));
179168
}
180169

170+
/**
171+
* {@inheritDoc}
172+
*/
173+
@Override
174+
@SuppressWarnings("unchecked")
175+
public <E, App extends Applicative<?, App>, TravB extends Traversable<E, Choice4<A, B, C, ?>>,
176+
AppTrav extends Applicative<TravB, App>> AppTrav traverse(Fn1<? super D, ? extends Applicative<E, App>> fn,
177+
Fn1<? super TravB, ? extends AppTrav> pure) {
178+
return match(a -> pure.apply((TravB) Choice4.<A, B, C, E>a(a)).coerce(),
179+
b -> pure.apply((TravB) Choice4.<A, B, C, E>b(b)).coerce(),
180+
c -> pure.apply((TravB) Choice4.<A, B, C, E>c(c)),
181+
d -> fn.apply(d).<Choice4<A, B, C, E>>fmap(Choice4::d).<TravB>fmap(Functor::coerce).coerce());
182+
}
183+
181184
/**
182185
* Static factory method for wrapping a value of type <code>A</code> in a {@link Choice4}.
183186
*

src/main/java/com/jnape/palatable/lambda/adt/choice/Choice5.java

Lines changed: 8 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -159,17 +159,14 @@ public <F> Choice5<A, B, C, D, F> flatMap(Fn1<? super E, ? extends Monad<F, Choi
159159
* {@inheritDoc}
160160
*/
161161
@Override
162-
public <F> Choice5<A, B, C, D, F> trampolineM(Fn1<? super E, ? extends MonadRec<RecursiveResult<E, F>, Choice5<A, B, C, D, ?>>> fn) {
163-
return match(Choice5::a,
164-
Choice5::b,
165-
Choice5::c,
166-
Choice5::d,
167-
trampoline(e -> fn.apply(e).<Choice5<A, B, C, D, RecursiveResult<E, F>>>coerce().match(
168-
a -> terminate(Choice5.a(a)),
169-
b -> terminate(Choice5.b(b)),
170-
c -> terminate(Choice5.c(c)),
171-
d -> terminate(Choice5.d(d)),
172-
eRec -> eRec.fmap(Choice5::e))));
162+
public <F> Choice5<A, B, C, D, F> trampolineM(
163+
Fn1<? super E, ? extends MonadRec<RecursiveResult<E, F>, Choice5<A, B, C, D, ?>>> fn) {
164+
return flatMap(trampoline(e -> fn.apply(e).<Choice5<A, B, C, D, RecursiveResult<E, F>>>coerce().match(
165+
a -> terminate(Choice5.a(a)),
166+
b -> terminate(Choice5.b(b)),
167+
c -> terminate(Choice5.c(c)),
168+
d -> terminate(Choice5.d(d)),
169+
eRec -> eRec.fmap(Choice5::e))));
173170
}
174171

175172
/**

src/main/java/com/jnape/palatable/lambda/adt/choice/Choice6.java

Lines changed: 24 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -6,16 +6,20 @@
66
import com.jnape.palatable.lambda.adt.hlist.HList;
77
import com.jnape.palatable.lambda.adt.hlist.Tuple6;
88
import com.jnape.palatable.lambda.functions.Fn1;
9+
import com.jnape.palatable.lambda.functions.recursion.RecursiveResult;
910
import com.jnape.palatable.lambda.functions.specialized.Pure;
1011
import com.jnape.palatable.lambda.functor.Applicative;
1112
import com.jnape.palatable.lambda.functor.Bifunctor;
1213
import com.jnape.palatable.lambda.functor.builtin.Lazy;
1314
import com.jnape.palatable.lambda.monad.Monad;
15+
import com.jnape.palatable.lambda.monad.MonadRec;
1416
import com.jnape.palatable.lambda.traversable.Traversable;
1517

1618
import java.util.Objects;
1719

1820
import static com.jnape.palatable.lambda.functions.builtin.fn2.Into6.into6;
21+
import static com.jnape.palatable.lambda.functions.recursion.RecursiveResult.terminate;
22+
import static com.jnape.palatable.lambda.functions.recursion.Trampoline.trampoline;
1923
import static com.jnape.palatable.lambda.functor.builtin.Lazy.lazy;
2024

2125
/**
@@ -32,7 +36,7 @@
3236
*/
3337
public abstract class Choice6<A, B, C, D, E, F> implements
3438
CoProduct6<A, B, C, D, E, F, Choice6<A, B, C, D, E, F>>,
35-
Monad<F, Choice6<A, B, C, D, E, ?>>,
39+
MonadRec<F, Choice6<A, B, C, D, E, ?>>,
3640
Bifunctor<E, F, Choice6<A, B, C, D, ?, ?>>,
3741
Traversable<F, Choice6<A, B, C, D, E, ?>> {
3842

@@ -71,7 +75,7 @@ public Choice5<A, B, C, D, E> converge(Fn1<? super F, ? extends CoProduct5<A, B,
7175
*/
7276
@Override
7377
public <G> Choice6<A, B, C, D, E, G> fmap(Fn1<? super F, ? extends G> fn) {
74-
return Monad.super.<G>fmap(fn).coerce();
78+
return MonadRec.super.<G>fmap(fn).coerce();
7579
}
7680

7781
/**
@@ -115,7 +119,7 @@ public <G> Choice6<A, B, C, D, E, G> pure(G g) {
115119
@Override
116120
public <G> Choice6<A, B, C, D, E, G> zip(
117121
Applicative<Fn1<? super F, ? extends G>, Choice6<A, B, C, D, E, ?>> appFn) {
118-
return Monad.super.zip(appFn).coerce();
122+
return MonadRec.super.zip(appFn).coerce();
119123
}
120124

121125
/**
@@ -137,15 +141,15 @@ public <G> Lazy<Choice6<A, B, C, D, E, G>> lazyZip(
137141
*/
138142
@Override
139143
public <G> Choice6<A, B, C, D, E, G> discardL(Applicative<G, Choice6<A, B, C, D, E, ?>> appB) {
140-
return Monad.super.discardL(appB).coerce();
144+
return MonadRec.super.discardL(appB).coerce();
141145
}
142146

143147
/**
144148
* {@inheritDoc}
145149
*/
146150
@Override
147151
public <G> Choice6<A, B, C, D, E, F> discardR(Applicative<G, Choice6<A, B, C, D, E, ?>> appB) {
148-
return Monad.super.discardR(appB).coerce();
152+
return MonadRec.super.discardR(appB).coerce();
149153
}
150154

151155
/**
@@ -156,6 +160,21 @@ public <G> Choice6<A, B, C, D, E, G> flatMap(Fn1<? super F, ? extends Monad<G, C
156160
return match(Choice6::a, Choice6::b, Choice6::c, Choice6::d, Choice6::e, f -> fn.apply(f).coerce());
157161
}
158162

163+
/**
164+
* {@inheritDoc}
165+
*/
166+
@Override
167+
public <G> Choice6<A, B, C, D, E, G> trampolineM(
168+
Fn1<? super F, ? extends MonadRec<RecursiveResult<F, G>, Choice6<A, B, C, D, E, ?>>> fn) {
169+
return flatMap(trampoline(f -> fn.apply(f).<Choice6<A, B, C, D, E, RecursiveResult<F, G>>>coerce().match(
170+
a -> terminate(Choice6.a(a)),
171+
b -> terminate(Choice6.b(b)),
172+
c -> terminate(Choice6.c(c)),
173+
d -> terminate(Choice6.d(d)),
174+
e -> terminate(Choice6.e(e)),
175+
fRec -> fRec.fmap(Choice6::f))));
176+
}
177+
159178
/**
160179
* {@inheritDoc}
161180
*/

src/main/java/com/jnape/palatable/lambda/adt/choice/Choice7.java

Lines changed: 25 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -6,16 +6,20 @@
66
import com.jnape.palatable.lambda.adt.hlist.HList;
77
import com.jnape.palatable.lambda.adt.hlist.Tuple7;
88
import com.jnape.palatable.lambda.functions.Fn1;
9+
import com.jnape.palatable.lambda.functions.recursion.RecursiveResult;
910
import com.jnape.palatable.lambda.functions.specialized.Pure;
1011
import com.jnape.palatable.lambda.functor.Applicative;
1112
import com.jnape.palatable.lambda.functor.Bifunctor;
1213
import com.jnape.palatable.lambda.functor.builtin.Lazy;
1314
import com.jnape.palatable.lambda.monad.Monad;
15+
import com.jnape.palatable.lambda.monad.MonadRec;
1416
import com.jnape.palatable.lambda.traversable.Traversable;
1517

1618
import java.util.Objects;
1719

1820
import static com.jnape.palatable.lambda.functions.builtin.fn2.Into7.into7;
21+
import static com.jnape.palatable.lambda.functions.recursion.RecursiveResult.terminate;
22+
import static com.jnape.palatable.lambda.functions.recursion.Trampoline.trampoline;
1923
import static com.jnape.palatable.lambda.functor.builtin.Lazy.lazy;
2024

2125
/**
@@ -33,7 +37,7 @@
3337
*/
3438
public abstract class Choice7<A, B, C, D, E, F, G> implements
3539
CoProduct7<A, B, C, D, E, F, G, Choice7<A, B, C, D, E, F, G>>,
36-
Monad<G, Choice7<A, B, C, D, E, F, ?>>,
40+
MonadRec<G, Choice7<A, B, C, D, E, F, ?>>,
3741
Bifunctor<F, G, Choice7<A, B, C, D, E, ?, ?>>,
3842
Traversable<G, Choice7<A, B, C, D, E, F, ?>> {
3943

@@ -73,7 +77,7 @@ public Choice6<A, B, C, D, E, F> converge(Fn1<? super G, ? extends CoProduct6<A,
7377
*/
7478
@Override
7579
public <H> Choice7<A, B, C, D, E, F, H> fmap(Fn1<? super G, ? extends H> fn) {
76-
return Monad.super.<H>fmap(fn).coerce();
80+
return MonadRec.super.<H>fmap(fn).coerce();
7781
}
7882

7983
/**
@@ -115,7 +119,7 @@ public <H> Choice7<A, B, C, D, E, F, H> pure(H h) {
115119
@Override
116120
public <H> Choice7<A, B, C, D, E, F, H> zip(
117121
Applicative<Fn1<? super G, ? extends H>, Choice7<A, B, C, D, E, F, ?>> appFn) {
118-
return Monad.super.zip(appFn).coerce();
122+
return MonadRec.super.zip(appFn).coerce();
119123
}
120124

121125
/**
@@ -138,15 +142,15 @@ public <H> Lazy<Choice7<A, B, C, D, E, F, H>> lazyZip(
138142
*/
139143
@Override
140144
public <H> Choice7<A, B, C, D, E, F, H> discardL(Applicative<H, Choice7<A, B, C, D, E, F, ?>> appB) {
141-
return Monad.super.discardL(appB).coerce();
145+
return MonadRec.super.discardL(appB).coerce();
142146
}
143147

144148
/**
145149
* {@inheritDoc}
146150
*/
147151
@Override
148152
public <H> Choice7<A, B, C, D, E, F, G> discardR(Applicative<H, Choice7<A, B, C, D, E, F, ?>> appB) {
149-
return Monad.super.discardR(appB).coerce();
153+
return MonadRec.super.discardR(appB).coerce();
150154
}
151155

152156
/**
@@ -158,6 +162,22 @@ public <H> Choice7<A, B, C, D, E, F, H> flatMap(
158162
return match(Choice7::a, Choice7::b, Choice7::c, Choice7::d, Choice7::e, Choice7::f, g -> fn.apply(g).coerce());
159163
}
160164

165+
/**
166+
* {@inheritDoc}
167+
*/
168+
@Override
169+
public <H> Choice7<A, B, C, D, E, F, H> trampolineM(
170+
Fn1<? super G, ? extends MonadRec<RecursiveResult<G, H>, Choice7<A, B, C, D, E, F, ?>>> fn) {
171+
return flatMap(trampoline(g -> fn.apply(g).<Choice7<A, B, C, D, E, F, RecursiveResult<G, H>>>coerce().match(
172+
a -> terminate(a(a)),
173+
b -> terminate(b(b)),
174+
c -> terminate(c(c)),
175+
d -> terminate(d(d)),
176+
e -> terminate(e(e)),
177+
f -> terminate(f(f)),
178+
gRec -> gRec.fmap(Choice7::g))));
179+
}
180+
161181
/**
162182
* {@inheritDoc}
163183
*/

0 commit comments

Comments
 (0)