Add Reader.flatMap() (#228)
* Add link to online Javadoc. * Add Reader.flatMap
This commit is contained in:
parent
5b09c1b525
commit
58796c8f73
4 changed files with 47 additions and 4 deletions
|
@ -14,6 +14,8 @@ https://oss.sonatype.org/content/repositories/releases/net/kemitix/mon/)
|
|||
https://img.shields.io/maven-central/v/net.kemitix/mon.svg?style=for-the-badge)](
|
||||
https://search.maven.org/artifact/net.kemitix/mon)
|
||||
|
||||
The documentation below is being slowly migrated to [Javadoc](https://kemitix.github.io/mon/).
|
||||
|
||||
- [Maven Usage](#Maven-Usage)
|
||||
- [Wrapper](#Wrapper) - light-weight type-alias-like
|
||||
- [TypeAlias](#TypeAlias) - type-alias-like monadic wrapper
|
||||
|
|
2
pom.xml
2
pom.xml
|
@ -11,7 +11,7 @@
|
|||
</parent>
|
||||
|
||||
<artifactId>mon</artifactId>
|
||||
<version>3.2.0</version>
|
||||
<version>3.3.0</version>
|
||||
|
||||
<name>Mon</name>
|
||||
<description>Wrapper, TypeAlias, Maybe, Result, Tree, Lazy, Either and Combinators for Java.
|
||||
|
|
|
@ -44,7 +44,21 @@ public interface Reader<E, R> {
|
|||
* @return a new Reader to provided the result of the supplied function
|
||||
*/
|
||||
@API(status = API.Status.EXPERIMENTAL)
|
||||
default <V> Reader<E, V> andThen(BiFunction<E, R, V> f) {
|
||||
default <V> Reader<E, V> flatMap(BiFunction<E, R, V> f) {
|
||||
return env -> f.apply(env, run(env));
|
||||
}
|
||||
|
||||
/**
|
||||
* Applies the function provided to the reader when run, and executes that
|
||||
* resulting reader.
|
||||
*
|
||||
* @param f the function which takes the previously generated value and
|
||||
* produces another Reader
|
||||
* @param <V> the type of the value the new Reader returns
|
||||
* @return a new Reader
|
||||
*/
|
||||
@API(status = API.Status.EXPERIMENTAL)
|
||||
default <V> Reader<E, V> flatMap(Function<R, Reader<E, V>> f) {
|
||||
return env -> f.apply(run(env)).run(env);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,6 +6,7 @@ import org.junit.jupiter.api.DisplayName;
|
|||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import java.util.concurrent.atomic.AtomicInteger;
|
||||
import java.util.function.Function;
|
||||
|
||||
public class ReaderTest
|
||||
implements WithAssertions {
|
||||
|
@ -66,8 +67,8 @@ public class ReaderTest
|
|||
};
|
||||
Reader<Environment, String> program =
|
||||
((Reader<Environment, Integer>) e -> e.intValue())
|
||||
.andThen((e, i) -> e.intValue() + (i * 2))
|
||||
.andThen((e, i) -> String.format("%.2f",
|
||||
.flatMap((e, i) -> e.intValue() + (i * 2))
|
||||
.flatMap((e, i) -> String.format("%.2f",
|
||||
i.floatValue() / e.intValue()));
|
||||
//when
|
||||
String result = program.run(env);
|
||||
|
@ -75,6 +76,32 @@ public class ReaderTest
|
|||
assertThat(result).isEqualTo("2.96");// ((123 * 2) + (123 + 1)) / (123 + 2)
|
||||
}
|
||||
|
||||
@Test
|
||||
@DisplayName("flatMap")
|
||||
void flatMap() {
|
||||
//given
|
||||
AtomicInteger value = new AtomicInteger(123);
|
||||
Environment env = new Environment() {
|
||||
@Override
|
||||
public Integer intValue() {
|
||||
return value.incrementAndGet();
|
||||
}
|
||||
};
|
||||
Function<Integer, Reader<Environment, Integer>> addNextValue =
|
||||
integer -> (Reader<Environment, Integer>) e -> e.intValue() + integer;
|
||||
Function<Integer, Reader<Environment, Float>> divideByNextValue =
|
||||
integer -> (Reader<Environment, Float>) e -> integer.floatValue() / e.intValue();
|
||||
Reader<Environment, String> program =
|
||||
((Reader<Environment, Integer>) e -> e.intValue())
|
||||
.flatMap(addNextValue)
|
||||
.flatMap(divideByNextValue)
|
||||
.map(f -> String.format("%.3f", f));
|
||||
//when
|
||||
String result = program.run(env);
|
||||
//then
|
||||
assertThat(result).isEqualTo("1.976");// (123 + 124) / 125
|
||||
}
|
||||
|
||||
private interface Environment {
|
||||
|
||||
Integer intValue();
|
||||
|
|
Loading…
Reference in a new issue