All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.infinispan.util.DistinctKeyDoubleEntryCloseableIterator Maven / Gradle / Ivy

There is a newer version: 9.1.7.Final
Show newest version
package org.infinispan.util;

import org.infinispan.commons.util.CloseableIterator;
import org.infinispan.container.entries.CacheEntry;

import java.util.HashSet;
import java.util.NoSuchElementException;
import java.util.Set;
import java.util.function.Function;

public class DistinctKeyDoubleEntryCloseableIterator implements CloseableIterator {
   private final CloseableIterator iterator1;
   private final CloseableIterator iterator2;
   private final Function function;
   private final Set keysSeenInFirst;

   private boolean completedFirst = false;
   private E iterator2Next;

   public DistinctKeyDoubleEntryCloseableIterator(CloseableIterator first,
                                                  CloseableIterator second,
                                                  Function function,
                                                  Set seenKeys) {
      this.iterator1 = first;
      this.iterator2 = second;
      this.function = function;
      this.keysSeenInFirst = seenKeys;
   }

   @Override
   public void close() {
      try {
         iterator1.close();
      } catch (Throwable t1) {
         try {
            iterator2.close();
         } catch (Throwable t2) {
            t1.addSuppressed(t2);
         }
         throw t1;
      }
      iterator2.close();
   }

   @Override
   public boolean hasNext() {
      boolean hasNext;
      if (!completedFirst) {
         hasNext = iterator1.hasNext();
         if (hasNext) {
            return hasNext;
         } else {
            completedFirst = true;
         }
      }

      while (iterator2.hasNext()) {
         E e = iterator2.next();
         if (!keysSeenInFirst.remove(function.apply(e))) {
            iterator2Next = e;
            break;
         }
      }
      return iterator2Next != null;
   }

   @Override
   public E next() {
      E next;
      if (!completedFirst) {
         // We have to double check hasNext in case if they are calling next without hasNext
         if (iterator1.hasNext()) {
            next = iterator1.next();
            keysSeenInFirst.add(function.apply(next));
            return next;
         } else {
            completedFirst = true;
         }
      }

      E e;
      if (iterator2Next != null) {
         e = iterator2Next;
         iterator2Next = null;
         return e;
      }
      while(iterator2.hasNext()) {
         e = iterator2.next();
         if (!keysSeenInFirst.remove(function.apply(e))) {
            return e;
         }
      }
      throw new NoSuchElementException();
   }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy