Advertisement
Guest User

Java 8 optionalMap Example

a guest
Nov 2nd, 2012
47
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Java 5.61 KB | None | 0 0
  1. public interface OptionalMapper<T, R> {
  2.     Optional<R> optionalMap(T t);
  3. }
  4.  
  5. public class OptionalMapOp<T, R> implements IntermediateOp<T, R> {
  6.     public final OptionalMapper<? super T, ? extends R> mapper;
  7.  
  8.     public OptionalMapOp(OptionalMapper<? super T, ? extends R> mapper) {
  9.         this.mapper = Objects.requireNonNull(mapper);
  10.     }
  11.  
  12.     @Override
  13.     public int getOpFlags() {
  14.         return 1;   // TODO
  15.         //return StreamOpFlags.NOT_SORTED | StreamOpFlags.NOT_DISTINCT;
  16.     }
  17.  
  18.     @Override
  19.     public Iterator<R> wrapIterator(int flags, final Iterator<T> source) {
  20.         return iterator(source, mapper);
  21.     }
  22.  
  23.     @Override
  24.     public Sink<T> wrapSink(int flags, Sink sink) {
  25.         return new Sink.ChainedValue<T>(sink) {
  26.             @Override
  27.             public void accept(T t) {
  28.                 for (R r : Optionals.toIterable(mapper.optionalMap(t))) {
  29.                     downstream.accept(r);
  30.                 }
  31.             }
  32.         };
  33.     }
  34.  
  35.     public static<T, R> Iterator<R> iterator(final Iterator<T> source, final OptionalMapper<? super T, ? extends R> mapper) {
  36.         Objects.requireNonNull(source);
  37.         Objects.requireNonNull(mapper);
  38.  
  39.         return new OptionalMapIterator(source, mapper);
  40.     }
  41.  
  42.     static class OptionalMapIterator<T, R> implements Iterator<R> {
  43.         final Iterator<T> source;
  44.         final OptionalMapper<? super T, ? extends R> mapper;
  45.  
  46.         boolean haveNext = false;
  47.         Optional<? extends R> nextValue = Optional.<R>empty();
  48.  
  49.         OptionalMapIterator(final Iterator<T> source, final OptionalMapper<? super T, ? extends R> mapper) {
  50.             this.source = source;
  51.             this.mapper = mapper;
  52.         }
  53.  
  54.         public void tryToGetNext() {
  55.             if (!haveNext) {
  56.                 while (source.hasNext()) {
  57.                     final T sourceNext = source.next();
  58.                     nextValue = mapper.optionalMap(sourceNext);
  59.  
  60.                     if (nextValue.isPresent()) {
  61.                         haveNext = true;
  62.                         return;
  63.                     }
  64.                 }
  65.             }
  66.         }
  67.  
  68.         @Override
  69.         public boolean hasNext() {
  70.             tryToGetNext();
  71.             return haveNext;
  72.         }
  73.  
  74.         @Override
  75.         public R next() {
  76.             tryToGetNext();
  77.  
  78.             if (haveNext) {
  79.                 final Optional<? extends R> result = nextValue;
  80.                 haveNext = false;
  81.                 nextValue = Optional.<R>empty();
  82.                 return result.get();
  83.             } else {
  84.                 throw new NoSuchElementException();
  85.             }
  86.         }
  87.     }
  88. }
  89.  
  90. public class MoreStreams {
  91.     // This is a quick and dirty example that works.
  92.     // The cast and the generic types would have to be fixed for a non-throwaway implementation.
  93.     public static <T, R> Stream<R> optionalMap(Stream<T> stream, OptionalMapper<? super T, R> mapper) {
  94.         final ValuePipeline vp = (ValuePipeline) stream;
  95.         final OptionalMapOp mapOp = new OptionalMapOp<>(mapper);
  96.         return chainValue(vp, mapOp);
  97.     }
  98.  
  99.     protected static <E_IN, E_OUT> Stream<E_OUT> chainValue(AbstractPipeline<E_IN, E_OUT> pipeline, IntermediateOp<E_OUT, E_OUT> op) {
  100.         return new ValuePipeline<>(pipeline, op);
  101.     }
  102. }
  103.  
  104. public class ZipCodeTest {
  105.     public static class Address {
  106.         public final Optional<String> zipOption;
  107.         public Address(Optional<String> zipOption) { this.zipOption = zipOption; }
  108.     }
  109.     public static class Person {
  110.         public final Optional<Address> addressOption;
  111.         public Person(Optional<Address> addressOption) { this.addressOption = addressOption; }
  112.     }
  113.  
  114.     public static void main(String[] args) {
  115.         List<Person> people = new ArrayList<Person>();
  116.         people.add(new Person(Optional.<Address>empty()));
  117.         people.add(new Person(new Optional(new Address(Optional.<String>empty()))));
  118.         people.add(new Person(new Optional(new Address(new Optional("12345")))));
  119.         people.add(new Person(new Optional(new Address(Optional.<String>empty()))));
  120.         people.add(new Person(new Optional(new Address(new Optional("45678")))));
  121.         people.add(new Person(new Optional(new Address(new Optional("98765")))));
  122.         people.add(new Person(Optional.<Address>empty()));
  123.  
  124.         Stream<Person> s = people.stream();
  125.         ValuePipeline vp = (ValuePipeline) s;
  126.  
  127.         // --------------------------------------------------------
  128.         // Regular map example: JDK8 supports this...
  129.  
  130.         final List<Optional<Address>> optAddresses = new ArrayList<Optional<Address>>();
  131.         // Using static function syntax to match later examples:
  132.         MoreStreams.map(people.stream(), (p) -> p.addressOption).into(optAddresses);
  133.         // Nicer Syntax is built into JDK:
  134.         people.stream().map((p) -> p.addressOption).into(optAddresses);
  135.  
  136.         // --------------------------------------------------------
  137.         // optionalMap(flatMap) example: JDK8 purposefully omits...
  138.  
  139.         final List<Address> addresses = new ArrayList<Address>();
  140.         optionalMap(people.stream(), (p) -> p.addressOption).into(addresses);
  141.         // If JDK8 had this built-in, the nicer syntax would be :
  142.         //people.stream().optionalMap((p) -> p.addressOption).into(addresses);
  143.  
  144.         final List<String> zips = new ArrayList<String>();
  145.         optionalMap(optionalMap(people.stream(), (p) -> p.addressOption), (a) -> a.zipOption).into(zips);
  146.         // If JDK8 had this built-in, the nicer syntax would be :
  147.         //people.stream().optionalMap((p) -> p.addressOption).optionalMap((a) -> a.zipOption).into(zips);
  148.     }
  149. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement