From 59efc034a88fa6263629c48687edbedaf3073096 Mon Sep 17 00:00:00 2001 From: Jacob Signorovitch Date: Wed, 26 Mar 2025 09:30:27 -0400 Subject: [PATCH] There are things that have been done. --- optionals/.project | 11 ++++ optionals/src/optionals/Main.java | 90 ++++++++++++++++++++++++++++--- 2 files changed, 95 insertions(+), 6 deletions(-) diff --git a/optionals/.project b/optionals/.project index 1917593..d24053b 100644 --- a/optionals/.project +++ b/optionals/.project @@ -14,4 +14,15 @@ org.eclipse.jdt.core.javanature + + + 1741281320906 + + 30 + + org.eclipse.core.resources.regexFilterMatcher + node_modules|\.git|__CREATED_BY_JAVA_LANGUAGE_SERVER__ + + + diff --git a/optionals/src/optionals/Main.java b/optionals/src/optionals/Main.java index e882597..bfd3247 100644 --- a/optionals/src/optionals/Main.java +++ b/optionals/src/optionals/Main.java @@ -1,42 +1,120 @@ package optionals; +import java.util.ArrayList; +import java.util.Arrays; import java.util.List; import java.util.Optional; import java.util.function.Function; import java.util.function.Predicate; +import tester.Tester; class OptionalUtils { // Return the list of `f()` applied to every element in `xs`, but do not // include the empty results. static List convertPassing(List xs, Function> f) { - return null; + return dropEmpty(xs.stream().map(f).toList()); } // Return the list of `f()` applied to every element in `xs`, but do not // include the resuslts that don't pass `pred()`. static List convertPassing(List xs, Function f, Predicate pred) { - return null; + return xs.stream().map(f).filter(pred).toList(); } // Drop all empty values. static List dropEmpty(List> xs) { - return xs.stream().filter(Optional::isEmpty); + return xs + .stream() // Convert to stream. + .filter(Optional::isPresent) // Filter out empty. + .map(Optional::get) // Extract value from optional. + .toList(); // Convert back to list. } // Return a new function that applies `f()` to non-null values and returns // empty optionals on null values. static Function> nullFriendly(Function f) { - return null; + // f() could still return NULL, doesn't check that case. + return x -> x == null ? Optional.empty() : Optional.of(f.apply(x)); } // Apply and to the boolean values if both are present, otherwise return // empty optional. static Optional optionalAnd(Optional b1, Optional b2) { - return null; + return b1.isPresent() && b2.isPresent() + ? Optional.of(b1.get() && b2.get()) + : Optional.empty(); } } -class Examples {} +class Examples { + List> things = List.of( + Optional.of("Hello,"), Optional.empty(), Optional.of(" "), + Optional.of("world."), Optional.empty() + ); + + List thingsMissing = + new ArrayList<>(Arrays.asList("Hello,", null, " ", "world.", null)); + + List thingsFrobnicated = + List.of(",olleH,olleH", " ", ".dlrow.dlrow"); + + Optional decide(String s) { + return s.length() == 3 ? Optional.of(s.substring(0, 1)) + : Optional.empty(); + } + + Boolean judge(String s) { return s.contains("h"); } + String augment(String s) { return s.repeat(2); } + String frobnicate(String s) { + return new StringBuilder(s).reverse().toString().repeat(2); + } + + void testDropEmpty(Tester t) { + t.checkExpect( + OptionalUtils.dropEmpty(things), List.of("Hello,", " ", "world.") + ); + } + + void testConvertPassing(Tester t) { + t.checkExpect( + OptionalUtils.convertPassing( + List.of("ndsf", "asd", "hjkl"), this::decide + ), + List.of("a") + ); + + t.checkExpect( + OptionalUtils.convertPassing( + List.of("uff", "fhf", "hek", "uyr"), this::augment, this::judge + ), + List.of("fhffhf", "hekhek") + ); + } + + void testNullFriendly(Tester t) { + t.checkExpect( + OptionalUtils.convertPassing( + thingsMissing, OptionalUtils.nullFriendly(this::frobnicate) + ), + thingsFrobnicated + ); + } + + void testOptionalAnd(Tester t) { + t.checkExpect( + OptionalUtils.optionalAnd(Optional.of(true), Optional.of(true)), + Optional.of(true) + ); + t.checkExpect( + OptionalUtils.optionalAnd(Optional.of(true), Optional.of(false)), + Optional.of(false) + ); + t.checkExpect( + OptionalUtils.optionalAnd(Optional.of(true), Optional.empty()), + Optional.empty() + ); + } +}