Skip to content

Instantly share code, notes, and snippets.

@gneuvill
Last active May 1, 2016 12:03
Show Gist options
  • Save gneuvill/a4a75ef89b04651c0378 to your computer and use it in GitHub Desktop.
Save gneuvill/a4a75ef89b04651c0378 to your computer and use it in GitHub Desktop.
// given...
class Person {
final String name;
final Integer age;
final Date birth;
Person(String name, Integer age, Date birth) {
this.name = name;
this.age = age;
this.birth = birth;
}
}
Maybe<String> getName(String id) {
return id.equals("toto") ? Just("Toto Titi") : Nothing();
}
Maybe<Integer> getAge(String id) {
return id.equals("toto") ? Just(36) : Nothing();
}
Maybe<Date> getBirthDate(String name, Integer age) {
return name.equals("Toto Titi") && age < 40 ? Just(new Date()) : Nothing();
}
// ...we can express
// Monadic Do
Maybe<Person> maybePers = Do
.$(Maybe.instances, Maybe::narrow
, () -> getName("toto")
, __ -> getAge("toto")
, (name, age) -> getBirthDate(name, age)
, Person::new);
// Interleaved Dos
Maybe<Person> maybePers2 = Do
.$(Maybe.instances, Maybe::narrow
, () -> getName("toto")
, __ -> getAge("toto")
, (name, age) -> Do
.$(Maybe.instances, Maybe::narrow
, () -> getBirthDate(name, age)
, bd -> new Person(name, age, bd)) // interleaved Dos...
, (String __, Integer ___, Person p) -> p); // ... need some help
// A test on Eithers created on the fly ; type inference seems to cope with it...
Either<String, Person> personOrError = Do
.$(Either.instances(), Either::narrow
, () -> getName("toto").toEither(() -> "error getting name")
, __ -> getAge("toto").toEither(() -> "error getting age")
, (name, age) -> getBirthDate(name, age).toEither(() -> "error getting birth date")
, Person::new);
// applicative Do
Maybe<Person> apMaybePers = ApDo.
$(Maybe.instances, Maybe::narrow
, getName("toto")
, getAge("toto")
, Just(new Date())
, Person::new);
// Traversing on...
List<Maybe<String>> maybes =
Cons(Just("a"), Cons(Just("b"), Cons(Just("c"), Nil())));
// ... the nice way
Maybe<List<String>> listMaybe1 = List.sequenceMaybe(maybes);
// ... the less nice (but possible, just in case the short cut isn't available) way
Maybe<List<String>> listMaybe2 =
Maybe.narrow(List.instances.sequence(List::narrow, Maybe.instances, maybes));
@clinuxrulz
Copy link

clinuxrulz commented May 1, 2016

I've also come up with a poor man's do notation. But I think it still has some security problems. Your input could be valuable.
see: highj/highj#13

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment